You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
61 lines
2.4 KiB
61 lines
2.4 KiB
"Functions that help with dynamically creating decorators for views." |
|
|
|
import types |
|
try: |
|
from functools import wraps |
|
except ImportError: |
|
from django.utils.functional import wraps # Python 2.3, 2.4 fallback. |
|
|
|
def decorator_from_middleware(middleware_class): |
|
""" |
|
Given a middleware class (not an instance), returns a view decorator. This |
|
lets you use middleware functionality on a per-view basis. |
|
""" |
|
def _decorator_from_middleware(*args, **kwargs): |
|
# For historical reasons, these "decorators" are also called as |
|
# dec(func, *args) instead of dec(*args)(func). We handle both forms |
|
# for backwards compatibility. |
|
has_func = True |
|
try: |
|
view_func = kwargs.pop('view_func') |
|
except KeyError: |
|
if len(args): |
|
view_func, args = args[0], args[1:] |
|
else: |
|
has_func = False |
|
if not (has_func and isinstance(view_func, types.FunctionType)): |
|
# We are being called as a decorator. |
|
if has_func: |
|
args = (view_func,) + args |
|
middleware = middleware_class(*args, **kwargs) |
|
|
|
def decorator_func(fn): |
|
return _decorator_from_middleware(fn, *args, **kwargs) |
|
return decorator_func |
|
|
|
middleware = middleware_class(*args, **kwargs) |
|
|
|
def _wrapped_view(request, *args, **kwargs): |
|
if hasattr(middleware, 'process_request'): |
|
result = middleware.process_request(request) |
|
if result is not None: |
|
return result |
|
if hasattr(middleware, 'process_view'): |
|
result = middleware.process_view(request, view_func, args, kwargs) |
|
if result is not None: |
|
return result |
|
try: |
|
response = view_func(request, *args, **kwargs) |
|
except Exception, e: |
|
if hasattr(middleware, 'process_exception'): |
|
result = middleware.process_exception(request, e) |
|
if result is not None: |
|
return result |
|
raise |
|
if hasattr(middleware, 'process_response'): |
|
result = middleware.process_response(request, response) |
|
if result is not None: |
|
return result |
|
return response |
|
return wraps(view_func)(_wrapped_view) |
|
return _decorator_from_middleware
|
|
|