Flask:RESTful API和SocketIO服务器

nma*_*rko 11 python flask flask-restful flask-socketio

背景

我正在尝试使用Flask-RESTful扩展创建一个简单的REST API.此API主要用于管理CRUD和用户身份验证以获得简单服务.

我还尝试使用Flask-SocketIO扩展创建一些Web套接字,这些用户可以连接到这些扩展,并查看与使用该服务的其他人相关的一些数据的实时更新.因此,我需要知道这些用户已经过身份验证并有权连接到某些套接字.

问题

但是,我在设置时遇到了一些麻烦.看起来我无法让这两个组件(REST API和SocketIO服务器)在同一个Flask实例上协同工作.我说这个的原因是因为当我运行以下命令时,REST API或SocketIO服务器都可以工作,但不能同时工作:

from flask import Flask
from flask_restful import Api
from flask.ext.socketio import SocketIO

app = Flask(__name__)

api = Api(app)
socketio = SocketIO(app)

# some test resources for the API and
# a test emitter statement for the SocketIO server
# are added here

if __name__ == '__main__':
    app.run(port=5000)
    socketio.run(app, port=5005)
Run Code Online (Sandbox Code Playgroud)

这种类型的设置的典型解决方案是同时具有两个不同的Flask实例吗?例如,我的SocketIO服务器是否必须向我的REST API发出请求才能检查特定用户是否经过身份验证/授权连接到特定套接字?

Sea*_*ira 20

您只想socketio.run(app, port=5005)在端口5005上运行并点击REST API.

这样做的原因是因为在幕后,Flask-SocketIO正在运行一个基于gevent(或1.0版本,也是eventlet)的公共网络服务器 - 这个服务器直接处理websocket请求(使用你通过socketio.on装饰器注册的处理程序)和将非websocket请求传递给Flask.

你的代码的原因没有工作是因为这两个app.runsocketio.run阻塞操作.无论哪一个先跑,都是循环,等待连接,永远不要让第二个开始.如果您确实需要在不同的端口上运行websocket连接,则需要run在不同的进程上生成socketio或app 调用.

  • 很好的答案,但我想要注意Flask-SocketIO即将打破对gevent的独占依赖.扩展的开发版本1.0a1可以使用gevent,eventlet甚至简单的Werkzeug(尽管后者在没有WebSocket支持的情况下运行). (6认同)