Clean up __before__ and __after__ handling and make it Python 3-compatible
--HG-- branch : py3kmaster
parent
232bb17d6f
commit
17cac57721
|
@ -90,40 +90,12 @@ class Application(object):
|
|||
start_response_wrapper = StartResponseWrapper(start_response)
|
||||
request.start_response = start_response_wrapper
|
||||
try:
|
||||
# If the callable has an __before__ attribute, call it
|
||||
if hasattr(func, '__before__'):
|
||||
func.__before__(request)
|
||||
# If the callable is an instance method and its class has
|
||||
# a __before__ method, call that
|
||||
elif hasattr(func, 'im_self') and \
|
||||
hasattr(func.im_self, '__before__'):
|
||||
func.im_self.__before__(request)
|
||||
# The callable might be a partial, so check the inner func
|
||||
elif hasattr(func, 'func'):
|
||||
if hasattr(func.func, '__before__'):
|
||||
func.func.__before__(request)
|
||||
elif hasattr(func.func, 'im_self') and \
|
||||
hasattr(func.func.im_self, '__before__'):
|
||||
func.func.im_self.__before__(request)
|
||||
self._call_before(func)(request)
|
||||
response = func(request)
|
||||
except WSGIHTTPException as e:
|
||||
return e(environ, start_response)
|
||||
finally:
|
||||
# If the callable has an __after__ method, call it
|
||||
if hasattr(func, '__after__'):
|
||||
func.__after__(request)
|
||||
# If the callable is an instance method and its class has
|
||||
# an __after__ method, call that
|
||||
elif hasattr(func, 'im_self') and \
|
||||
hasattr(func.im_self, '__after__'):
|
||||
func.im_self.__after__(request)
|
||||
# The callable might be a partial, so check the inner func
|
||||
elif hasattr(func, 'func'):
|
||||
if hasattr(func.func, '__after__'):
|
||||
func.func.__after__(request)
|
||||
elif hasattr(func.func, 'im_self') and \
|
||||
hasattr(func.func.im_self, '__after__'):
|
||||
func.func.im_self.__after__(request)
|
||||
self._call_after(func)(request)
|
||||
|
||||
# The callable might have returned just a string, which is OK,
|
||||
# but we need to wrap it in a Response object
|
||||
|
@ -141,6 +113,31 @@ class Application(object):
|
|||
start_response(response.status, response.headerlist)
|
||||
if not environ['REQUEST_METHOD'] == 'HEAD':
|
||||
return response.app_iter
|
||||
|
||||
def _call_after(self, func):
|
||||
try:
|
||||
return self._find_attr(func, '__after__')
|
||||
except AttributeError:
|
||||
return lambda r: None
|
||||
|
||||
def _call_before(self, func):
|
||||
try:
|
||||
return self._find_attr(func, '__before__')
|
||||
except AttributeError:
|
||||
return lambda r: None
|
||||
|
||||
def _find_attr(self, obj, attr):
|
||||
try:
|
||||
# Object has the specified attribute itself
|
||||
return getattr(obj, attr)
|
||||
except AttributeError:
|
||||
# Object is a bound method; look for the attribute on the instance
|
||||
if hasattr(obj, '__self__'):
|
||||
return self._find_attr(obj.__self__, attr)
|
||||
# Object is a partial; look for the attribute on the inner function
|
||||
elif hasattr(obj, 'func'):
|
||||
return self._find_attr(obj.func, attr)
|
||||
raise
|
||||
|
||||
class StartResponseWrapper():
|
||||
|
||||
|
|
Loading…
Reference in New Issue