我正在开发我的第一个Flask应用程序.直接从
this中获取一些代码,我试图确保用户的cookie中存在一个值.
def after_this_request(f): if not hasattr(g,'after_request_callbacks'): g.after_request_callbacks = [] g.after_request_callbacks.append(f) return f @app.after_request def call_after_request_callbacks(response): for callback in getattr(g,'after_request_callbacks',()): response = callback(response) return response @app.before_request def detect_unique_id(): unique_id = request.cookies.get('unique_id') if unique_id is None: unique_id = generate_unique_id() @after_this_request def remember_unique_id(response): response.set_cookie('unique_id',unique_id) g.unique_id = unique_id
我一直收到这个错误:
Traceback (most recent call last): File "/..../env/lib/python2.7/site-packages/flask/app.py",line 1701,in __call__ return self.wsgi_app(environ,start_response) File "/..../env/lib/python2.7/site-packages/flask/app.py",line 1690,in wsgi_app return response(environ,start_response) TypeError: 'NoneType' object is not callable
我试图了解这个错误的原因.请帮忙.
解决方法
问题
remember_unique_id不返回响应对象,但call_after_request_callbacks将调用通过after_this_request装饰器添加的每个回调的结果分配给结果,然后返回它.也就是说:
# This for callback in getattr(g,()): response = callback(response) # translates to this for callback in [remember_unique_id]: response = callback(response) # which translates to this response = remember_unique_id(response) # which translates to this response = None
解决方案
或者:
>更新remember_unique_id以返回已修改的响应对象
>更新call_after_request_callbacks以检查返回的对象并确保它不是None:
for callback in getattr(g,()): result = callback(response) if result is not None: response = result
为什么会这样?
Flask是一个WSGI应用程序,它希望响应是一个WSGI应用程序(即一个可调用的对象).当它处理来自视图模板的响应时,它会运行一些检查以确保它可以用作响应对象,如果返回的值不是WSGI应用程序,则将其转换为一个.它不会检查响应对象是否未被after_request修饰符更改,因此当它尝试调用响应对象时(此时它假定它是一个有效的WSGI应用程序),您将获得TypeError.