mirror of
https://github.com/django/django.git
synced 2024-12-22 09:05:43 +00:00
Refs #31949 -- Made @no_append_slash decorator to work with async functions.
This commit is contained in:
parent
e5c844d6f2
commit
23abec9192
@ -1,5 +1,7 @@
|
||||
from functools import wraps
|
||||
|
||||
from asgiref.sync import iscoroutinefunction
|
||||
|
||||
|
||||
def no_append_slash(view_func):
|
||||
"""
|
||||
@ -9,9 +11,17 @@ def no_append_slash(view_func):
|
||||
|
||||
# view_func.should_append_slash = False would also work, but decorators are
|
||||
# nicer if they don't have side effects, so return a new function.
|
||||
@wraps(view_func)
|
||||
def wrapper_view(*args, **kwargs):
|
||||
return view_func(*args, **kwargs)
|
||||
|
||||
wrapper_view.should_append_slash = False
|
||||
return wrapper_view
|
||||
if iscoroutinefunction(view_func):
|
||||
|
||||
async def _view_wrapper(request, *args, **kwargs):
|
||||
return await view_func(request, *args, **kwargs)
|
||||
|
||||
else:
|
||||
|
||||
def _view_wrapper(request, *args, **kwargs):
|
||||
return view_func(request, *args, **kwargs)
|
||||
|
||||
_view_wrapper.should_append_slash = False
|
||||
|
||||
return wraps(view_func)(_view_wrapper)
|
||||
|
@ -237,6 +237,7 @@ Decorators
|
||||
|
||||
* :func:`~django.views.decorators.cache.cache_control`
|
||||
* :func:`~django.views.decorators.cache.never_cache`
|
||||
* :func:`~django.views.decorators.common.no_append_slash`
|
||||
* ``xframe_options_deny()``
|
||||
* ``xframe_options_sameorigin()``
|
||||
* ``xframe_options_exempt()``
|
||||
|
@ -83,6 +83,7 @@ view functions:
|
||||
|
||||
* :func:`~django.views.decorators.cache.cache_control`
|
||||
* :func:`~django.views.decorators.cache.never_cache`
|
||||
* :func:`~django.views.decorators.common.no_append_slash`
|
||||
* ``xframe_options_deny()``
|
||||
* ``xframe_options_sameorigin()``
|
||||
* ``xframe_options_exempt()``
|
||||
|
@ -147,3 +147,7 @@ customization of :class:`~django.middleware.common.CommonMiddleware` behavior.
|
||||
|
||||
This decorator allows individual views to be excluded from
|
||||
:setting:`APPEND_SLASH` URL normalization.
|
||||
|
||||
.. versionchanged:: 5.0
|
||||
|
||||
Support for wrapping asynchronous view functions was added.
|
||||
|
37
tests/decorators/test_common.py
Normal file
37
tests/decorators/test_common.py
Normal file
@ -0,0 +1,37 @@
|
||||
from asgiref.sync import iscoroutinefunction
|
||||
|
||||
from django.http import HttpRequest, HttpResponse
|
||||
from django.test import SimpleTestCase
|
||||
from django.views.decorators.common import no_append_slash
|
||||
|
||||
|
||||
class NoAppendSlashTests(SimpleTestCase):
|
||||
def test_wrapped_sync_function_is_not_coroutine_function(self):
|
||||
def sync_view(request):
|
||||
return HttpResponse()
|
||||
|
||||
wrapped_view = no_append_slash(sync_view)
|
||||
self.assertIs(iscoroutinefunction(wrapped_view), False)
|
||||
|
||||
def test_wrapped_async_function_is_coroutine_function(self):
|
||||
async def async_view(request):
|
||||
return HttpResponse()
|
||||
|
||||
wrapped_view = no_append_slash(async_view)
|
||||
self.assertIs(iscoroutinefunction(wrapped_view), True)
|
||||
|
||||
def test_no_append_slash_decorator(self):
|
||||
@no_append_slash
|
||||
def sync_view(request):
|
||||
return HttpResponse()
|
||||
|
||||
self.assertIs(sync_view.should_append_slash, False)
|
||||
self.assertIsInstance(sync_view(HttpRequest()), HttpResponse)
|
||||
|
||||
async def test_no_append_slash_decorator_async_view(self):
|
||||
@no_append_slash
|
||||
async def async_view(request):
|
||||
return HttpResponse()
|
||||
|
||||
self.assertIs(async_view.should_append_slash, False)
|
||||
self.assertIsInstance(await async_view(HttpRequest()), HttpResponse)
|
Loading…
Reference in New Issue
Block a user