根据SO / SF和其他网站的建议,我使用CherryPy作为WSGI服务器来启动我使用Flask构建的Python Web服务器的多个实例。每个实例都在自己的端口上运行,并且位于Nginx之后。我应该注意下面的内容确实对我有用,但是我很困扰我以错误的方式处理了它并且它“偶然”起作用。
这是我当前的cherrypy.conf文件:
[global]
server.socket_host = '0.0.0.0'
server.socket_port = 8891
request.dispatch: cherrypy.dispatch.MethodDispatcher()
tree.mount = {'/':my_flask_server.app}
如果没有深入我的Flask服务器,这是它的开始:
import flask
app = flask.Flask(__name__)
@app.route('/')
def hello_world():
return "hello"
这是我在命令行上发布的命令,用于启动Cherryd:
cherryd -c cherrypy.conf -i my_flask_server
问题是:
在CherryPy中包装Flask仍然是在生产中使用Flask的首选方法吗? https://stackoverflow.com/questions/4884541/cherrypy-vs-flask-werkzeug
这是使用.conf文件启动CherryPy并导入Flask应用程序的正确方法吗?我已经搜索过CherryPy文档,但是我找不到任何与我在这里特别想做的用例匹配的用例。
在一台计算机上启动多个CherryPy / Flask实例的正确方法是执行多个cherryd命令(使用-d等进行守护程序),并为每个要使用的端口使用唯一的.conf文件(8891,8892,等等)?或者是否有更好的“CherryPy”方法来实现这一目标?
感谢您的帮助和见解。
答案 0 :(得分:5)
我不能代表Flask,但我可以为CherryPy说话。这看起来像是“正确的方式”......大多数情况下。关于MethodDispatcher的那一行是一个无操作,因为它只影响CherryPy应用程序,你似乎没有安装任何(只改为一个Flask应用程序)。
关于第3点,你说得对。 CherryPy允许您在同一进程中运行多个Server对象,以便侦听多个端口(或协议),但它没有任何糖来启动多个进程。正如你所说,具有不同配置文件的多个cherryd命令是如何做到的(除非你想使用更集成的集群/配置管理工具,如eggmonster)。
答案 1 :(得分:3)
原则上,这是通过cherrypy提供烧瓶应用程序的正确方法,只需快速记下您的命名:
值得注意的是tree.mount
本身不是配置键 - tree
将导致使用参数cherrypy._cpconfig._tree_config_handler(k, v)
调用'mount', {'/': my_flask_server.app}
。
_tree_config_handler
根本不使用关键参数,因此在您的配置中,“mount”只是路径映射的特定字典的任意标签。它也没有“挂载”应用程序(毕竟它不是CherryPy应用程序)。我的意思是,它不是cherrypy.tree.mount(…)
它而是cherrypy.tree.graft
一个任意的WSGI处理程序到你的“脚本名称”(路径,但在CherryPy术语中)命名空间。
Cherrypy的日志消息有点误导性地说“已安装< app as string> on /”]
这是一个有点重要的一点,因为对于移植而言,与mount不同,您无法为应用程序指定其他选项,例如静态文件服务或在该路径上指定流式响应。
所以我建议将tree.mount
配置密钥更改为描述性的内容,不要过多地读取有关CherryPy中发生的内容的语义(因为是 cherrypy.tree.mount
方法)由于该配置。例如,tree.flask_app_name
如果您只是映射该dict中的一个应用程序(可能有许多tree
指令,所有这些指令只是合并到路径名称空间中)或tree.wsgi_delegates
如果您在该字典中映射许多应用程序。
另一方面,如果你想要像为您的应用程序提供静态文件服务,您不必创建一个样板文件樱桃应用程序来保存该配置。您只需使用适当的附加配置挂载None
即可。如果将CherryPy放入启动cherryd以提供静态内容的目录中,则以下文件就足以让CherryPy从子目录'static'提供静态内容(调用cherryd作为cherryd -c cherrypy.conf -i my_flask_server -i static
:
import cherrypy
# next line could also have config as an inline dict, but
# file config is often easier to handle
cherrypy.tree.mount(None, '/static-path', 'static.conf')
# static.conf
[/]
tools.staticdir.on = True
tools.staticdir.root = os.getcwd()
tools.staticdir.dir = 'static'
tools.staticdir.index = 'index.html'