使用app.mount时,尝试在URL路径中使用特殊字符会失败:
http://127.0.0.1:8080/test/äöü
结果:
Error: 400 Bad Request
Invalid path string. Expected UTF-8
test.py:
#!/usr/bin/python
import bottle
import testapp
bottle.debug(True)
app = bottle.Bottle()
app.mount('/test',testapp.app)
app.run(reloader=True, host='0.0.0.0', port=8080)
run(host="localhost",port=8080)
testapp.py:
import bottle
app = bottle.Bottle()
@app.route("/:category", method=["GET","POST"])
def admin(category):
try:
return category
except Exception(e):
print ("e:"+str(e))
当不使用app.mount时,相同的代码运行良好:
test_working.py:
#!/usr/bin/python
# -*- coding: utf-8 -*-
import bottle
import testapp
bottle.debug(True)
app = bottle.Bottle()
@app.route("/test/:category", method=["GET","POST"])
def admin(category):
try:
return category
except Exception(e):
print ("e:"+str(e))
app.run(reloader=True, host='0.0.0.0', port=8080)
run(host="localhost",port=8080)
这看起来像是一个错误,或者我在这里遗漏了什么? :/
答案 0 :(得分:2)
是的,因为这似乎是瓶子里的一个错误。
问题在于_handle
方法:
def _handle(self, environ):
path = environ['bottle.raw_path'] = environ['PATH_INFO']
if py3k:
try:
environ['PATH_INFO'] = path.encode('latin1').decode('utf8')
except UnicodeError:
return HTTPError(400, 'Invalid path string. Expected UTF-8')
此处environ['PATH_INFO']
转换为utf8,因此当为安装的应用程序再次调用相同的方法时,内容将已经是utf8,因此转换将失败。
一个非常快速的解决方法是将代码更改为跳过转换(如果已经完成):
def _handle(self, environ):
converted = 'bottle.raw_path' in environ
path = environ['bottle.raw_path'] = environ['PATH_INFO']
if py3k and not converted:
try:
environ['PATH_INFO'] = path.encode('latin1').decode('utf8')
except UnicodeError:
return HTTPError(400, 'Invalid path string. Expected UTF-8')
提交针对瓶子的错误报告可能会很好。