如何让 SocketIO 在本地工作时在 Docker 中工作?
How can I get SocketIO to work in Docker when it's working locally?
当我 运行 flask run -p 8000
时,我的 Flask 应用程序在本地运行,但是当我尝试 运行 在 Docker 中执行此操作时,我的 SocketIO 事件似乎没有通过从服务器到客户端。
这是一个示例应用程序来说明我的意思:
Flask 应用程序:
import flask
from flask import Flask, render_template
from flask_socketio import SocketIO, emit
import requests
import logging
import time
import os
app = Flask(__name__)
app.config['SECRET_KEY'] = 'secret!'
socketio = SocketIO(app, logger=False, engineio_logger=False)
# Flask App
@app.route('/')
def index():
return render_template('index.html')
@socketio.on('hello')
def connected(message):
data = message
print('Message received from browser:', data)
# Thanks I got your message
emit('reply', {'data': 'Hello browser. I received your message.'})
if __name__ == '__main__':
app.run(debug=True,host='0.0.0.0',port=int(os.environ.get('PORT', 8000)))
Docker文件:
FROM tiangolo/uwsgi-nginx-flask:python3.6-alpine3.7
RUN apk add g++
RUN apk add linux-headers
RUN apk add libc-dev
RUN apk add musl-dev
COPY requirements.txt /
RUN python -m pip install --upgrade pip
RUN pip3 install numpy
RUN pip install -r /requirements.txt
COPY . /
WORKDIR /
ENV PORT 8000
RUN chmod +x ./gunicorn_starter.sh
ENTRYPOINT ["sh","./gunicorn_starter.sh"]
gunicorn_starter.sh:
#!/bin/bash
gunicorn --chdir / app:app -w 2 --threads 2 --workers 1 -b 0.0.0.0:8000
它 运行 从 Docker 开始真的很慢而且 SocketIO 事件似乎没有注册。这是我看到的错误:
[2022-01-27 20:35:31 +0000] [9] [ERROR] Error handling request /socket.io/?EIO=3&transport=websocket&sid=7862ffa61dcc4c1abbf38c368975d2b9
Traceback (most recent call last):
File "/usr/lib/python3.6/site-packages/gunicorn/workers/gthread.py", line 279, in handle
keepalive = self.handle_request(req, conn)
File "/usr/lib/python3.6/site-packages/gunicorn/workers/gthread.py", line 336, in handle_request
resp.close()
File "/usr/lib/python3.6/site-packages/gunicorn/http/wsgi.py", line 409, in close
self.send_headers()
File "/usr/lib/python3.6/site-packages/gunicorn/http/wsgi.py", line 325, in send_headers
tosend = self.default_headers()
File "/usr/lib/python3.6/site-packages/gunicorn/http/wsgi.py", line 306, in default_headers
elif self.should_close():
File "/usr/lib/python3.6/site-packages/gunicorn/http/wsgi.py", line 229, in should_close
if self.status_code < 200 or self.status_code in (204, 304):
AttributeError: 'Response' object has no attribute 'status_code'
我最终在我的 Dockerfile 中使用了这个命令,它成功了:
CMD ["gunicorn", "--bind", "0.0.0.0:8000", "--workers", "1", "--worker-class", "eventlet", "app:app"]
当我 运行 flask run -p 8000
时,我的 Flask 应用程序在本地运行,但是当我尝试 运行 在 Docker 中执行此操作时,我的 SocketIO 事件似乎没有通过从服务器到客户端。
这是一个示例应用程序来说明我的意思:
Flask 应用程序:
import flask
from flask import Flask, render_template
from flask_socketio import SocketIO, emit
import requests
import logging
import time
import os
app = Flask(__name__)
app.config['SECRET_KEY'] = 'secret!'
socketio = SocketIO(app, logger=False, engineio_logger=False)
# Flask App
@app.route('/')
def index():
return render_template('index.html')
@socketio.on('hello')
def connected(message):
data = message
print('Message received from browser:', data)
# Thanks I got your message
emit('reply', {'data': 'Hello browser. I received your message.'})
if __name__ == '__main__':
app.run(debug=True,host='0.0.0.0',port=int(os.environ.get('PORT', 8000)))
Docker文件:
FROM tiangolo/uwsgi-nginx-flask:python3.6-alpine3.7
RUN apk add g++
RUN apk add linux-headers
RUN apk add libc-dev
RUN apk add musl-dev
COPY requirements.txt /
RUN python -m pip install --upgrade pip
RUN pip3 install numpy
RUN pip install -r /requirements.txt
COPY . /
WORKDIR /
ENV PORT 8000
RUN chmod +x ./gunicorn_starter.sh
ENTRYPOINT ["sh","./gunicorn_starter.sh"]
gunicorn_starter.sh:
#!/bin/bash
gunicorn --chdir / app:app -w 2 --threads 2 --workers 1 -b 0.0.0.0:8000
它 运行 从 Docker 开始真的很慢而且 SocketIO 事件似乎没有注册。这是我看到的错误:
[2022-01-27 20:35:31 +0000] [9] [ERROR] Error handling request /socket.io/?EIO=3&transport=websocket&sid=7862ffa61dcc4c1abbf38c368975d2b9
Traceback (most recent call last):
File "/usr/lib/python3.6/site-packages/gunicorn/workers/gthread.py", line 279, in handle
keepalive = self.handle_request(req, conn)
File "/usr/lib/python3.6/site-packages/gunicorn/workers/gthread.py", line 336, in handle_request
resp.close()
File "/usr/lib/python3.6/site-packages/gunicorn/http/wsgi.py", line 409, in close
self.send_headers()
File "/usr/lib/python3.6/site-packages/gunicorn/http/wsgi.py", line 325, in send_headers
tosend = self.default_headers()
File "/usr/lib/python3.6/site-packages/gunicorn/http/wsgi.py", line 306, in default_headers
elif self.should_close():
File "/usr/lib/python3.6/site-packages/gunicorn/http/wsgi.py", line 229, in should_close
if self.status_code < 200 or self.status_code in (204, 304):
AttributeError: 'Response' object has no attribute 'status_code'
我最终在我的 Dockerfile 中使用了这个命令,它成功了:
CMD ["gunicorn", "--bind", "0.0.0.0:8000", "--workers", "1", "--worker-class", "eventlet", "app:app"]