我有一个Flask应用程序,该应用程序在进行某些休息时正在使用ProcessPoolExecutor运行多个模块。
更新:将redis添加为消息队列(使用docker,将redis用作redis的主机)
socketio = SocketIO(app, message_queue='redis://redis')
(...)
def emit_event(evt, message):
socketio.emit(evt, message, namespace='/test')
@app.route('/info', methods=['GET'])
def info():
emit_event('update_reports', '')
(...)
if __name__ == "__main__":
socketio.run(host='0.0.0.0', threaded=True)
现在我添加了redis,当从主应用发出时,它仍然可以工作。 这里有一些我正在运行子流程的代码:
def __init__(self):
self.executor = futures.ProcessPoolExecutor(max_workers=4)
self.socketio = SocketIO(async_mode='eventlet', message_queue='redis://redis')
(...)
future = self.executor.submit(process, params)
future.add_done_callback(functools.partial(self.finished_callback, pid))
然后在该回调中,我调用emit_event
方法:
def finished_callback(self, pid, future):
pid.status = Status.DONE.value
pid.finished_at = datetime.datetime.utcnow
pid.save()
self.socketio.emit('update_reports', 'done', namespace='/test')
从我的控制器获取/发送/从客户端发送消息的工作正常,即使我从curl或postman调用/ info,我的客户端也会收到消息-但是-在尝试从内部发送事件的方式相同时子进程回调,现在显示此错误:
这主要用于通知,例如通知长时间的过程何时完成以及类似的事情。
INFO:socketio:emitting event "update_reports" to all [/test]
ERROR:socketio:Cannot publish to redis... retrying
ERROR:socketio:Cannot publish to redis... giving up
我做错了什么?
谢谢!
答案 0 :(得分:1)
在设置Flask-SocketIO扩展以便外部进程可以发出时,需要遵循一些特定规则,其中包括使用消息队列,主进程和外部进程用于协调工作。有关说明,请参见文档的Emitting from an External Process部分。