Skip to content

Commit 22cb614

Browse files
authored
Get dataclass declaration scope locals with inspect.currentframe() (#187)
inspect.stack() can be very costly, especially when called with context=1: it has to get information about source files / lines etc. This gets very slow when using dozens of dataclasses in some large-ish codebases (where stacks can be relatively deep). Also add the frame when class_schema() is called directly.
1 parent f4d04de commit 22cb614

File tree

1 file changed

+12
-1
lines changed

1 file changed

+12
-1
lines changed

marshmallow_dataclass/__init__.py

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -150,7 +150,12 @@ def dataclass(
150150
dc = dataclasses.dataclass( # type: ignore
151151
_cls, repr=repr, eq=eq, order=order, unsafe_hash=unsafe_hash, frozen=frozen
152152
)
153-
cls_frame = cls_frame or inspect.stack()[1][0]
153+
if not cls_frame:
154+
current_frame = inspect.currentframe()
155+
if current_frame:
156+
cls_frame = current_frame.f_back
157+
# Per https://docs.python.org/3/library/inspect.html#the-interpreter-stack
158+
del current_frame
154159
if _cls is None:
155160
return lambda cls: add_schema(dc(cls), base_schema, cls_frame=cls_frame)
156161
return add_schema(dc, base_schema, cls_frame=cls_frame)
@@ -336,6 +341,12 @@ def class_schema(
336341
"""
337342
if not dataclasses.is_dataclass(clazz):
338343
clazz = dataclasses.dataclass(clazz)
344+
if not clazz_frame:
345+
current_frame = inspect.currentframe()
346+
if current_frame:
347+
clazz_frame = current_frame.f_back
348+
# Per https://docs.python.org/3/library/inspect.html#the-interpreter-stack
349+
del current_frame
339350
return _internal_class_schema(clazz, base_schema, clazz_frame)
340351

341352

0 commit comments

Comments
 (0)