使用Flask+Gunicorn+Supervisor+Nginx把应用部署到服务器时,出现了编码问题。
File "/srv/www/biu/venv/lib/python3.4/site-packages/werkzeug/datastructures.py",
line 2653, in save
dst = open(dst, 'wb')
UnicodeEncodeError: 'ascii' codec can't encode characters
in position 56-60: ordinal not in range(128)
文件名的确有中文,但是在本地测试的时候没有问题啊!在本地采用的是'UTF-8'进行编码,但是在服务器怎么就是'ASCII'了?
在Python How-To中,查到了以下信息:
Most of the operating systems in common use today support filenames that contain arbitrary Unicode characters.
Usually this is implemented by converting the Unicode string into some encoding that varies depending on the system.
For example, Mac OS X uses UTF-8 while Windows uses a configurable encoding; on Windows, Python uses the name “mbcs” to refer to whatever the currently configured encoding is.
On Unix systems, there will only be a filesystem encoding if you’ve set the LANG or LC_CTYPE environment variables;
if you haven’t, the default encoding is UTF-8.
在Ubuntu上存文件时,文件名是按照LANG
的设定来encode
的。看了看服务器上的设置为:
abuntu@abuntu:~$ echo $LANG
en_US.UTF-8
abuntu@abuntu:~$
没问题啊啊啊
不用Supervisor
,手动启动Gunicorn
,发现编码错误又没啦。那肯定就是Gunicron
的问题啊。
Gunicorn
的配置项中有user
的配置,之前配的是www-data
。尝试着将user
改为当前登陆的用户abuntu
,居然特么的就好了!!!
原来是www-data
的LANG设置是'ASCII'。把user
改成abuntu
算了。
Update 03.28
昨天明明是按照上面的分析改了supervisor 的user
字段,运行了一下没问题啊。
但是今天又特么出现编码问题了。可能是昨天搞得太晚,测试时仍旧用的是手动启动的Gunicorn吧。
查到了这篇文章, 果真如其所言,手动启动的Gunicorn 的locale
是 ('en_US', 'UTF-8')
, 而用Supervisor启动的是(None, None)
。
尝试用locale.setlocale(locale.LC_ALL,'en_US.UTF-8')
,结果还是不行。
然后通过搜索关键字 gunicorn locale
查到了解决方案
在Supervisor
的配置文件/etc/supervisor/supervisor.conf
的[supervisord]
项目下,加入以下内容即可解决问题
environment=LANG=en_US.UTF-8,LC_ALL=en_US.UTF-8,LC_LANG=en_US.UTF-8
参见官方文档