Uvicorn + Django + NGinx - 处理 websockets 时出现错误 404

Uvicorn + Django + NGinx - Error 404 while handling websockets

我正在使用 Nginx 和 Uvicorn 设置一个服务器 运行 使用 websockets 的 Django 应用程序。

正常的 http 请求一切顺利,我可以获取我的网页,但我的 websockets 握手总是以 404 错误结束。

一切顺利运行运行server.

这是我的 asgi.py 文件

import os
import django
django.setup()

from channels.auth import AuthMiddlewareStack
from channels.routing import ProtocolTypeRouter, URLRouter
from django.core.asgi import get_asgi_application
import MYAPP.routing
import Stressing.routing

os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'MYAPP.settings')

application = ProtocolTypeRouter({
    "http": get_asgi_application(),
    "websocket": AuthMiddlewareStack( URLRouter( Stressing.routing.websocket_urlpatterns ) ),
    # Just HTTP for now. (We can add other protocols later.)
})

我的settings.py

ASGI_APPLICATION = 'MYAPP.asgi.application'

redis_host = os.environ.get('REDIS_HOST', '127.0.0.1')

CHANNEL_LAYERS = {
    'default': {
        'CONFIG': {
            'hosts': [(redis_host, 6379)],
        },
        'BACKEND': 'channels_redis.core.RedisChannelLayer',
    },
}

我的 nginx 配置文件

server {
    listen 80;
    server_name MYAPP.box 10.42.0.1;
    
    
    location = /favicon.ico { access_log off; log_not_found off; }
    location ~ ^/static {
        autoindex on;
        root /home/MYAPP;
    }

    location ~ ^/ {
        include proxy_params;
        proxy_pass http://unix:/home/MYAPP/MYAPP.sock;
    }
    location @proxy_to_app {
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header Host $http_host;
        proxy_redirect off;
        proxy_buffering off;
        
        proxy_pass http://unix:/home/MYAPP/MYAPP.sock;
    }
    location ~ ^/ws/ {
        proxy_pass http://unix:/home/MYAPP/MYAPP.sock;
        proxy_http_version 1.1;
        proxy_redirect off;
        proxy_buffering 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 Upgrade $http_upgrade;
        proxy_set_header Connection "Upgrade";
    }
}

正如我在 gunicorn 日志中看到的那样,请求似乎到达了套接字

not found /ws/0

有人知道问题的根源吗?

我已经从我的 Nginx 文件中删除了正则表达式,现在可以使用了

location ~ ^/ {
...
location ~ ^/ws/

变成了

location / {
...
location /ws/

这样就解决了。但是如果有人能给我解释一下背景呢? 我认为 Nginx 总是优先考虑最具体的路径。它只在没有正则表达式的情况下工作吗? (我想没有办法确定哪个正则表达式更具体?!)