部署期间的 django 通道问题
django channel issue during deployment
我正在使用 Django Channels 并使用 NGINX+Gunicorn+Uvicorn 进行部署,并遵循 Digital Ocean 的教程(即 https://www.digitalocean.com/community/tutorials/how-to-set-up-an-asgi-django-app-with-postgres-nginx-and-uvicorn-on-ubuntu-20-04)
当我尝试使用以下命令在没有 NGINX 的情况下 运行 站点 @ www.myproject.com:8000 时,我没有发现任何问题:
gunicorn --bind 0.0.0.0:8000 myproject.asgi -w 4 -k uvicorn.workers.UvicornWorker
但是,当我使用 NGINX 部署时,除了使用 django 频道的聊天功能页面外,大多数网站功能都可以。
websocket 以某种方式无法连接,如浏览器的错误所示:
WebSocket connection to 'ws://myproject.com/ws/chat/ADVPKG/' failed: Error during WebSocket handshake: Unexpected response code: 500
查看服务器的错误日志,我看到:
2022/01/06 08:13:02 [alert] 16624#16624: *8421 768 worker_connections are not enough while connecting to upstream, client: 127.0.0.1, server: www.myproject.com, request: "GET /ws/chat/ADVPKG/ HTTP/1.1", upstream: "http://127.0.0.1:80/ws/chat/ADVPKG/", host: "myproject.com"
下面是我的代码:
asgi.py
import os
os.environ['DJANGO_SETTINGS_MODULE'] = 'myproject.settings'
import django
django.setup()
from django.core.asgi import get_asgi_application
django_asgi_app = get_asgi_application()
from channels.auth import AuthMiddlewareStack
from channels.routing import ProtocolTypeRouter, URLRouter
import chat.routing
application = ProtocolTypeRouter({
"http": django_asgi_app,
"websocket": AuthMiddlewareStack(
URLRouter(
chat.routing.websocket_urlpatterns
)
),
})
/etc/nginx/sites-available/myproject
server {
listen 80;
server_name www.myproject.com
myproject.com
""
1X.XXX.XX.XXX
;
location = /favicon.ico { access_log off; log_not_found off; }
location /static/ {
root /home/ubuntu/stochie;
}
location /ws/ {
proxy_pass http://0.0.0.0;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection “upgrade”;
proxy_redirect off;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Host $server_name;
}
location / {
include proxy_params;
proxy_pass http://unix:/run/gunicorn.sock;
}
}
基本上:
- 我很确定问题出在 nginx 配置上,因为没有 nginx,每个功能都能完美运行
- 我严重怀疑 'proxy_pass http://0.0.0.0;' 可能是错误的,根据一份论坛问卷,这是由于代理传递点指向自身的无限循环。到目前为止,根据其他论坛问卷,我尝试了 'localhost'、'localhost:8000'、http://django、http://uvicorn 但无法解决问题。
我觉得是你的问题asgi.py
从您的 asgi.py
中删除路由并将此代码放入您的 asgi.py
import os
import django
from channels.routing import get_default_application
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'myproject.settings')
django.setup()
application = get_default_application()
然后在下面创建 routings.py
类似的内容,并将 myproject.routings.application
放入您的 settings.py
application = ProtocolTypeRouter({
'websocket': OriginValidator(
TokenAuthMiddleware(
URLRouter([
url(r"^ws/courier/$", CourierConsumer.as_asgi()),
url(r"^.*$", NoRouteFoundConsumer.as_asgi()),
])
),
['*'],
),
})
我正在使用 Django Channels 并使用 NGINX+Gunicorn+Uvicorn 进行部署,并遵循 Digital Ocean 的教程(即 https://www.digitalocean.com/community/tutorials/how-to-set-up-an-asgi-django-app-with-postgres-nginx-and-uvicorn-on-ubuntu-20-04)
当我尝试使用以下命令在没有 NGINX 的情况下 运行 站点 @ www.myproject.com:8000 时,我没有发现任何问题:
gunicorn --bind 0.0.0.0:8000 myproject.asgi -w 4 -k uvicorn.workers.UvicornWorker
但是,当我使用 NGINX 部署时,除了使用 django 频道的聊天功能页面外,大多数网站功能都可以。
websocket 以某种方式无法连接,如浏览器的错误所示:
WebSocket connection to 'ws://myproject.com/ws/chat/ADVPKG/' failed: Error during WebSocket handshake: Unexpected response code: 500
查看服务器的错误日志,我看到:
2022/01/06 08:13:02 [alert] 16624#16624: *8421 768 worker_connections are not enough while connecting to upstream, client: 127.0.0.1, server: www.myproject.com, request: "GET /ws/chat/ADVPKG/ HTTP/1.1", upstream: "http://127.0.0.1:80/ws/chat/ADVPKG/", host: "myproject.com"
下面是我的代码: asgi.py
import os
os.environ['DJANGO_SETTINGS_MODULE'] = 'myproject.settings'
import django
django.setup()
from django.core.asgi import get_asgi_application
django_asgi_app = get_asgi_application()
from channels.auth import AuthMiddlewareStack
from channels.routing import ProtocolTypeRouter, URLRouter
import chat.routing
application = ProtocolTypeRouter({
"http": django_asgi_app,
"websocket": AuthMiddlewareStack(
URLRouter(
chat.routing.websocket_urlpatterns
)
),
})
/etc/nginx/sites-available/myproject
server {
listen 80;
server_name www.myproject.com
myproject.com
""
1X.XXX.XX.XXX
;
location = /favicon.ico { access_log off; log_not_found off; }
location /static/ {
root /home/ubuntu/stochie;
}
location /ws/ {
proxy_pass http://0.0.0.0;
proxy_http_version 1.1;
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection “upgrade”;
proxy_redirect off;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Host $server_name;
}
location / {
include proxy_params;
proxy_pass http://unix:/run/gunicorn.sock;
}
}
基本上:
- 我很确定问题出在 nginx 配置上,因为没有 nginx,每个功能都能完美运行
- 我严重怀疑 'proxy_pass http://0.0.0.0;' 可能是错误的,根据一份论坛问卷,这是由于代理传递点指向自身的无限循环。到目前为止,根据其他论坛问卷,我尝试了 'localhost'、'localhost:8000'、http://django、http://uvicorn 但无法解决问题。
我觉得是你的问题asgi.py
从您的 asgi.py
中删除路由并将此代码放入您的 asgi.py
import os
import django
from channels.routing import get_default_application
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'myproject.settings')
django.setup()
application = get_default_application()
然后在下面创建 routings.py
类似的内容,并将 myproject.routings.application
放入您的 settings.py
application = ProtocolTypeRouter({
'websocket': OriginValidator(
TokenAuthMiddleware(
URLRouter([
url(r"^ws/courier/$", CourierConsumer.as_asgi()),
url(r"^.*$", NoRouteFoundConsumer.as_asgi()),
])
),
['*'],
),
})