Skip to content

Commit

Permalink
Support async view methods in extend_schema_view.
Browse files Browse the repository at this point in the history
  • Loading branch information
tbeadle committed Sep 12, 2024
1 parent 01ec586 commit e838e0c
Show file tree
Hide file tree
Showing 2 changed files with 21 additions and 5 deletions.
19 changes: 14 additions & 5 deletions drf_spectacular/drainage.py
Original file line number Diff line number Diff line change
Expand Up @@ -182,8 +182,12 @@ def get_view_method_names(view, schema=None) -> List[str]:
return [
item for item in dir(view) if callable(getattr(view, item)) and (
item in view.http_method_names
or item in schema.method_mapping.values()
or item == 'list'
or (
item in schema.async_method_mapping.values()
if view.view_is_async
else item in schema.method_mapping.values()
)
or item == ('alist' if view.view_is_async else 'list')
or hasattr(getattr(view, item), 'mapping')
)
]
Expand All @@ -202,9 +206,14 @@ def isolate_view_method(view, method_name):
if method_name in view.__dict__ and method.__name__ != 'handler':
return method

@functools.wraps(method)
def wrapped_method(self, request, *args, **kwargs):
return method(self, request, *args, **kwargs)
if getattr(view, "view_is_async", False):
@functools.wraps(method)
async def wrapped_method(self, request, *args, **kwargs):
return await method(self, request, *args, **kwargs)
else:
@functools.wraps(method)
def wrapped_method(self, request, *args, **kwargs):
return method(self, request, *args, **kwargs)

# wraps() will only create a shallow copy of method.__dict__. Updates to "kwargs"
# via @extend_schema would leak to the original method. Isolate by creating a copy.
Expand Down
7 changes: 7 additions & 0 deletions drf_spectacular/openapi.py
Original file line number Diff line number Diff line change
Expand Up @@ -57,6 +57,13 @@ class AutoSchema(ViewInspector):
'patch': 'partial_update',
'delete': 'destroy',
}
async_method_mapping = {
'get': 'aretrieve',
'post': 'acreate',
'put': 'aupdate',
'patch': 'partial_aupdate',
'delete': 'adestroy',
}

def get_operation(
self,
Expand Down

0 comments on commit e838e0c

Please sign in to comment.