如何在烧瓶socketio中保持活力?
Posted
技术标签:
【中文标题】如何在烧瓶socketio中保持活力?【英文标题】:how to keep alive in flask-socketio? 【发布时间】:2016-04-01 22:57:08 【问题描述】:我的烧瓶项目中有一个错误。 socketio 客户端经常与我的 flask-socketio 服务器断开连接。他们将在几分钟后重新连接。我想保持连接始终有效,我该怎么做? 如何修复此错误?
Traceback (most recent call last):
File "F:\Python27\lib\site-packages\gevent\pywsgi.py", line 846, in handle_one
_response
self.run_application()
File "F:\Python27\lib\site-packages\geventwebsocket\handler.py", line 76, in r
un_application
self.run_websocket()
File "F:\Python27\lib\site-packages\geventwebsocket\handler.py", line 52, in r
un_websocket
self.application(self.environ, lambda s, h, e=None: [])
File "F:\Python27\lib\site-packages\flask\app.py", line 1836, in __call__
return self.wsgi_app(environ, start_response)
File "F:\Python27\lib\site-packages\flask_socketio\__init__.py", line 37, in _
_call__
start_response)
File "F:\Python27\lib\site-packages\engineio\middleware.py", line 47, in __cal
l__
return self.engineio_app.handle_request(environ, start_response)
File "F:\Python27\lib\site-packages\socketio\server.py", line 303, in handle_r
equest
return self.eio.handle_request(environ, start_response)
File "F:\Python27\lib\site-packages\engineio\server.py", line 226, in handle_r
equest
environ, start_response)
File "F:\Python27\lib\site-packages\engineio\socket.py", line 75, in handle_ge
t_request
start_response)
File "F:\Python27\lib\site-packages\engineio\socket.py", line 110, in _upgrade
_websocket
return ws(environ, start_response)
File "F:\Python27\lib\site-packages\engineio\async_gevent.py", line 43, in __c
all__
return self.app(self)
File "F:\Python27\lib\site-packages\engineio\socket.py", line 171, in _websock
et_handler
self.receive(pkt)
File "F:\Python27\lib\site-packages\engineio\socket.py", line 45, in receive
self.server._trigger_event('message', self.sid, pkt.data)
File "F:\Python27\lib\site-packages\engineio\server.py", line 307, in _trigger
_event
return self.handlers[event](*args)
File "F:\Python27\lib\site-packages\socketio\server.py", line 423, in _handle_
eio_message
self._handle_event(sid, pkt.namespace, pkt.id, pkt.data)
File "F:\Python27\lib\site-packages\socketio\server.py", line 364, in _handle_
event
r = self._trigger_event(data[0], namespace, sid, *data[1:])
File "F:\Python27\lib\site-packages\socketio\server.py", line 391, in _trigger
_event
return self.handlers[namespace][event](*args)
File "F:\Python27\lib\site-packages\flask_socketio\__init__.py", line 147, in
_handler
app = self.server.environ[sid]['flask.app']
KeyError: 'e99ae44429294ef1af9b9012c6cd747c'
'GATEWAY_INTERFACE': 'CGI/1.1',
'HTTP_ACCEPT_ENCODING': 'gzip, deflate, sdch',
'HTTP_ACCEPT_LANGUAGE': 'zh-CN,zh;q=0.8,en;q=0.6',
'HTTP_CACHE_CONTROL': 'no-cache',
'HTTP_CONNECTION': 'Upgrade',
'HTTP_COOKIE': 'io=e99ae44429294ef1af9b9012c6cd747c; session=.eJyrVkrNTczMUbJSS
q_KyUzMS8_NzEvPKM10SM4vKtDLSy1JTSxO1UvOz1XSUUorzcnJS8xNBSqOKTWzsDAEkmYGqTGlFmkWl
kD5vMzkbKg8qmFKtQBXYyPB.CV-98A.aLaOqWHgFZILSx3w1JJ7V9RFUaE',
'HTTP_HOST': '127.0.0.1:5001',
'HTTP_ORIGIN': 'http://127.0.0.1:5001',
'HTTP_PRAGMA': 'no-cache',
'HTTP_SEC_WEBSOCKET_EXTENSIONS': 'permessage-deflate; client_max_window_bits',
'HTTP_SEC_WEBSOCKET_KEY': '7dsbtNi0XUWxPY3rXHn4MA==',
'HTTP_SEC_WEBSOCKET_VERSION': '13',
'HTTP_UPGRADE': 'websocket',
'HTTP_USER_AGENT': 'Mozilla/5.0 (Windows NT 6.1; WOW64) AppleWebKit/537.36 (KHT
ML, like Gecko) Chrome/47.0.2526.106 Safari/537.36',
'PATH_INFO': '/socket.io/',
'QUERY_STRING': 'EIO=3&transport=websocket&sid=e99ae44429294ef1af9b9012c6cd747c
',
'REMOTE_ADDR': '127.0.0.1',
'REMOTE_PORT': '2318',
'REQUEST_METHOD': 'GET',
'SCRIPT_NAME': '',
'SERVER_NAME': 'GIH-D-9660.game.ntes',
'SERVER_PORT': '5001',
'SERVER_PROTOCOL': 'HTTP/1.1',
'SERVER_SOFTWARE': 'gevent/1.1 Python/2.7',
'flask.app': <Flask 'views'>,
'wsgi.errors': <open file '<stderr>', mode 'w' at 0x0213D0D0>,
'wsgi.input': <gevent.pywsgi.Input object at 0x034255A8>,
'wsgi.multiprocess': False,
'wsgi.multithread': False,
'wsgi.run_once': False,
'wsgi.url_scheme': 'http',
'wsgi.version': (1, 0),
'wsgi.websocket': None,
'wsgi.websocket_version': '13' failed with KeyError
【问题讨论】:
【参考方案1】:请在服务器上启用 Engine.IO 日志记录(将参数 engineio_logger=True
添加到您的构造函数中),以便我们准确了解服务器所做的事情。
我的猜测是日志会显示服务器超时等待来自客户端的 ping 数据包,因此它假定客户端离开并关闭连接。 Socket.IO 协议要求客户端每隔一段时间发送这些特殊的 ping 数据包,如果没有发生,则服务器关闭连接。
根据您的错误,服务器似乎超时等待 ping 数据包并关闭了连接,但后来客户端确实发送了 ping 数据包,但已经太晚了。但是,这种情况下的错误消息可以改进,所以我会为此记录一个错误。
如果您设置的连接不可靠,您可以通过在SocketIO
构造函数中设置参数ping_timeout
来增加超时。默认值为 60 秒。
【讨论】:
Miguel:启用 engineio_logger=True 后,该日志文件位于何处(或者只是控制台输出)?我有同样的错误,我猜它是别的东西,但是这个错误被 socketio 的所有 handle_one 函数输出抑制了。 @KennyPowers 日志会转到控制台,除非您告诉它转到自定义日志记录对象。以上是关于如何在烧瓶socketio中保持活力?的主要内容,如果未能解决你的问题,请参考以下文章
在 Android 中解除绑定后,如何让服务与听众保持活力?