Nic*_*las 5 python unicode nginx flask
使用unicode_literals添加标头似乎与Nginx,uWSGI和一个简单的Flask应用程序失败:
# -*- coding: utf-8 -*-
from __future__ import unicode_literals
from flask import Flask, make_response
app = Flask('test')
@app.route('/')
def index():
response = make_response()
response.status_code = 401
response.headers = {'WWW-Authenticate': 'Basic realm="test"'} # Fail
# response.headers = {b'WWW-Authenticate': b'Basic realm="test"'} # Succeed
return response
if __name__ == '__main__':
app.run(debug=True)
Run Code Online (Sandbox Code Playgroud)
该应用程序可直接用于调试目的或通过Nginx - > uWSGI - > Flask并且运行良好.
WWW-Authenticate标题是正确的.Transfert-Encoding: chunked并丢弃WWW-Authenticate标头.强制b'...') format to add the header make the app works as expected in both cases.
The file is encoded in UTF-8 and there's abytestring (Python解释器的编码声明.我们使用的是Python 2.7.3,Nginx 1.4.2和uWSGI 1.3.
Nginx或uWSGI,Flask和unicode_literals之间是否存在任何已知的不兼容性?谢谢!
编辑:问题似乎来自uWSGI( https://github.com/unbit/uwsgi/blob/master/plugins/python/wsgi_headers.c#L116),因为它只检查PyString而不检查Python2的PyUnicode,如果我正确地理解了这段代码.
编辑:Armin Ronacher在5个月前修复了一个类似的错误(https://github.com/mitsuhiko/flask/issues/758),但我还没有在werkzeug git log中找到提交.我不知道修复程序是作用于redirect()函数还是更广泛地处理标头处理.我正在使用Werkzeug 0.9.4和Flask 0.10.1.
这个问题确实是由于Werkzeug中的错误造成的。正如您所注意到的,自 2013 年 6 月 4 日起,此问题已得到更正(参见Github 上的相关提交)。您可以使用版本0.9.5而不是0.9.4来获得 Werkzeug 的无错误版本。
此外,为了解决您的问题,我app.debug = True在 Flask 应用程序初始化后添加了它。这让我在 uWSGI 日志中收到以下错误:
Traceback (most recent call last):
File "/home/afigura/.virtualenvs/stack-python2/lib/python2.7/site-packages/flask/app.py", line 1836, in __call__
return self.wsgi_app(environ, start_response)
File "/home/afigura/.virtualenvs/stack-python2/lib/python2.7/site-packages/flask/app.py", line 1821, in wsgi_app
return response(environ, start_response)
File "/home/afigura/.virtualenvs/stack-python2/lib/python2.7/site-packages/werkzeug/wrappers.py", line 1201, in __call__
start_response(status, headers)
TypeError: http header key must be a string
Run Code Online (Sandbox Code Playgroud)
这与您在 Github 上发现的错误中提到的错误相对应。
因此,您可以使用以下解决方法来让Flask/Werkzeug使用unicode_literals:
response.headers = {b'WWW-Authenticate': 'Basic realm="test"'}
Run Code Online (Sandbox Code Playgroud)
或者:
response.headers = {str('WWW-Authenticate'): 'Basic realm="test"'}
Run Code Online (Sandbox Code Playgroud)
但如果可以的话,我建议您将 Werkzeug 版本更新为 >=0.9.5。
另外,请注意,虽然headersFlask/Werkzeug 响应的属性的行为类似于字典,但它实际上是一个Headers对象(请参阅Werkzeug 源代码)。因此,我建议您按如下方式使用它:
response.headers['WWW-Authenticate'] = 'Basic realm="test"'
Run Code Online (Sandbox Code Playgroud)
您可以在该函数的Flask 文档中看到一些关于此的示例make_response。
| 归档时间: |
|
| 查看次数: |
713 次 |
| 最近记录: |