如何解决 flask-socketio 的 ValueError('Invalid async_mode specified')?

How to solve ValueError('Invalid async_mode specified') for flask-socketio?

我正在 bitbucket 管道中测试 flask-socketio 服务器。它失败并显示以下消息:

Traceback (most recent call last):
  File "/root/.local/share/virtualenvs/build-3vGKWv3F/lib/python3.7/site-packages/flask_failsafe.py", line 29, in wrapper
    return func(*args, **kwargs)
  File "/opt/atlassian/pipelines/agent/build/main.py", line 89, in create_app
    return cell_data_api.create_app()
  File "/opt/atlassian/pipelines/agent/build/cell_data_api/__init__.py", line 30, in create_app
    socketio.init_app(app)
  File "/root/.local/share/virtualenvs/build-3vGKWv3F/lib/python3.7/site-packages/flask_socketio/__init__.py", line 243, in init_app
    self.server = socketio.Server(**self.server_options)
  File "/root/.local/share/virtualenvs/build-3vGKWv3F/lib/python3.7/site-packages/socketio/server.py", line 127, in __init__
    self.eio = self._engineio_server_class()(**engineio_options)
  File "/root/.local/share/virtualenvs/build-3vGKWv3F/lib/python3.7/site-packages/engineio/server.py", line 145, in __init__
    raise ValueError('Invalid async_mode specified')
ValueError: Invalid async_mode specified
Traceback (most recent call last):
  File "/.pyenv/versions/3.7.4/lib/python3.7/runpy.py", line 193, in _run_module_as_main
    "__main__", mod_spec)
  File "/.pyenv/versions/3.7.4/lib/python3.7/runpy.py", line 85, in _run_code
    exec(code, run_globals)
  File "/opt/atlassian/pipelines/agent/build/main.py", line 117, in <module>
    socketio.run(APP, host='0.0.0.0', port=8080, debug=True, use_reloader=True)
  File "/root/.local/share/virtualenvs/build-3vGKWv3F/lib/python3.7/site-packages/flask_socketio/__init__.py", line 564, in run
    if app.debug and self.server.eio.async_mode != 'threading':
AttributeError: 'NoneType' object has no attribute 'eio'

我的 main.py 文件如下所示:

import os
from cell_data_api import socketio

# Detect if we are running in App Engine
# Make sure this does NOT start if we are running a Cloud Function
if os.getenv('APP_ENGINE', '') == 'TRUE':
    import cell_data_api

    APP = cell_data_api.create_app()

if __name__ == '__main__':
    from flask_failsafe import failsafe

    @failsafe
    def create_app():
        # note that the import is *inside* this function so that we can catch
        # errors that happen at import time
        import cell_data_api

        # If `entrypoint` is not defined in app.yaml, App Engine will look for an app
        # called `app` in `main.py`.
        return cell_data_api.create_app()

    APP = create_app()

    # This is used when running locally only. When deploying to Google App
    # Engine, a webserver process such as Gunicorn will serve the app. This
    # can be configured by adding an `entrypoint` to app.yaml.
    socketio.run(APP, host='0.0.0.0', port=8080, debug=True, use_reloader=True)

Main.py 从 cell_data_api.py 导入,看起来像:

import os

from flask import Flask
from flask_cors import CORS
# import eventlet
from engineio.async_drivers import eventlet
from flask_socketio import SocketIO

socketio = SocketIO(
    always_connect=True,
    logger=True,
    async_mode=eventlet,
    cookie=...,
    ping_timeout=...
)


def create_app():
    # create and configure the app
    app = Flask(__name__)
    CORS(app)

    ......

    socketio.init_app(app)

    # ensure the instance folder exists
    try:
        os.makedirs(app.instance_path)
    except OSError:
        pass

    return app

我的环境是Python3.7,安装包:

[dev-packages]
alembic = "*"
flask_failsafe = "*"
wcwidth = "*"

[packages]
flask = "*"
absl-py = "*"
flask-cors = "*"
grpcio = "*"
transitions = "*"
sqlalchemy-json = "*"
sqlalchemy = "1.3.0"
flask_socketio='*'
eventlet='*'

与我发现的关于相同错误的其他两个问题不同,我没有使用 pyinstaller 或 cx_Freeze。

async_mode 参数以字符串作为参数。

而不是这个:

async_mode=eventlet,

这样做:

async_mode='eventlet',