从 APScheduler 作业发送 python-socket.io 消息导致客户端挂起

sou*_*rop 5 python socket.io apscheduler

我在应用程序中使用 APScheduler 来安排作业,并使用 python-socket.io 与浏览器客户端通信以通知其正在执行的作业。但是,我发现 socket.io 客户端(常规 JavaScript 客户端)不接受从计划作业发送的事件。

下面是一些部分代码。

# scheduler.py

sched = BackgroundScheduler() # with proper configuration and stuff
sched.start()

(...)

def add_job(method, param, time):
    start_time = datetime.now() + timedelta(seconds=time)
    trigger = DateTrigger(run_date=start_time)
    return sched.add_job(method, trigger=trigger, args=[param])

(...)
Run Code Online (Sandbox Code Playgroud)

在另一个脚本中,我这样称呼它:

# otherscript.py

import scheduler

(...)

def terminate(name):
    # Do some stuff
    sio.emit('ended', name)

def schedule_kill(name, time_offset):
    # Do some stuff
    scheduler.add_job(terminate, name, time_offset)

(...)
Run Code Online (Sandbox Code Playgroud)

terminate()是一个方法,它执行一些操作,然后调用python-socket.io以发出一条消息,表示它已结束。

socket.io 服务器在其他地方配置,功能完善,并导入为sio. 我可以很好地发送消息,除非我尝试通过已安排为作业的方法来发送消息。

python-engine.io似乎从日志中发送消息,但在客户端,不仅从未收到消息,而且客户端继续超时。这仅在它从计划作业接收到消息后发生,与之前一样,我仍然能够成功发送消息(通过常规方法调用)。

服务器日志:

[17:24:39] socketio  : emitting event "started" to all [/]
[17:24:39] engineio  : 5ab9e719cb2c492db2f46dfbd8385a55: Sending packet MESSAGE data 2["started","my_data"]
[17:24:39] scheduler : Scheduled terminate in 10 sec (at 2016-11-11 17:24:49.189081)
[17:24:42] socketio  : emitting event "started" to all [/]
[17:24:42] engineio  : 5ab9e719cb2c492db2f46dfbd8385a55: Sending packet MESSAGE data 2["started","test"]
[17:24:42] engineio  : 5ab9e719cb2c492db2f46dfbd8385a55: Received packet PING data None
[17:24:42] engineio  : 5ab9e719cb2c492db2f46dfbd8385a55: Sending packet PONG data None
[17:24:43] socketio  : emitting event "ended" to all [/]
[17:24:43] engineio  : 5ab9e719cb2c492db2f46dfbd8385a55: Sending packet MESSAGE data 2["ended","test"]
[17:24:49] socketio  : emitting event "ended" to all [/]
[17:24:49] engineio  : 5ab9e719cb2c492db2f46dfbd8385a55: Sending packet MESSAGE data 2["ended","my_data"]
[17:24:51] socketio  : emitting event "started" to all [/]
[17:24:51] engineio  : 5ab9e719cb2c492db2f46dfbd8385a55: Sending packet MESSAGE data 2["started","test"]
[17:24:52] socketio  : emitting event "ended" to all [/]
[17:24:52] engineio  : 5ab9e719cb2c492db2f46dfbd8385a55: Sending packet MESSAGE data 2["ended","test"]
[17:25:07] engineio  : 5ab9e719cb2c492db2f46dfbd8385a55: Received packet PING data None
[17:25:07] engineio  : 5ab9e719cb2c492db2f46dfbd8385a55: Sending packet PONG data None
Run Code Online (Sandbox Code Playgroud)

客户端日志:

engine.io-client:socket socket receive: type "message", data "2["started","my_data"]" +21s
engine.io-client:socket socket receive: type "message", data "2["started","test"]" +3s
engine.io-client:socket writing ping packet - expecting pong within 60000ms +524ms
engine.io-client:socket flushing 1 packets in socket +1ms
engine.io-client:socket socket receive: type "pong", data "undefined" +1ms
engine.io-client:socket socket receive: type "message", data "2["ended","test"]" +284ms
engine.io-client:socket writing ping packet - expecting pong within 60000ms +25s
engine.io-client:socket flushing 1 packets in socket +0ms
engine.io-client:socket socket close with reason: "ping timeout" +1m
Run Code Online (Sandbox Code Playgroud)

任何有关此问题的帮助将不胜感激。

小智 1

flask-socketio我在使用和 时遇到了问题APJobScheduler,我正在使用 的eventlet线程库flask-socketio。Monkey patching eventlet 解决了我的大部分问题。

正如 Miguel 所说,可能是由于socketio和使用的线程库不兼容APJobScheduler