@NyxDeveloper

Почему Channels посылает все сообщения в сокет только после обработки запроса?

Настроил Django в связке с Daphne через супервизор + Nginx на Ubuntu 20.04, само приложение запускается как ASGI. В приложении есть один долгий процесс создания файла с данными, для которого сделан сокет на получение информации о прогрессе обработки с процентом завершения. В этой долгой функции самым большим является цикл for, внутри которого в конце каждой итерации в канальный слой отправляется сообщение с данными прогресса.

Проблема состоит в том, что все сообщения приходят только после того, как запрос выполнится и клиент получит ответ от сервера, что спускает на нет всю идею. В чем может быть проблема?

Вот настройка ASGI:

import os

os.environ.setdefault("DJANGO_SETTINGS_MODULE", "asist.settings")

import django
from django.urls import path
from django.conf import settings

if not settings.configured:
    django.setup()

from .middleware import TokenAuthMiddleware
from channels.routing import ProtocolTypeRouter, URLRouter
from django.core.asgi import get_asgi_application

from document_parser import consumers as parser_consumers

application = ProtocolTypeRouter({
    "http": get_asgi_application(),
    "websocket": TokenAuthMiddleware(
        URLRouter(
            [
                path('backend/api/ws/progress/<str:token>/', parser_consumers.ProgressConsumer.as_asgi()),
            ]
        )
    ),
})


Вот настройка daphne в супервизоре:
[fcgi-program:asgi]
socket=tcp://localhost:8000
directory=/home/asist_backend_api/asist
command=daphne -u /run/daphne/daphne%(process_num)d.sock --fd 0 --access-log - --proxy-headers asist.asgi:application
numprocs=2
process_name=asgi%(process_num)d
autostart=true
autorestart=true
stdout_logfile=asgi.log
redirect_stderr=true


Вот, на всякий случай, конфиг nginx:
upstream asist_backend_api {
    server localhost:8000;
}

server {
    listen 80;
    server_name address.ya.ne.dam;

    proxy_read_timeout 100000;
    proxy_connect_timeout 100000;
    proxy_send_timeout 100000;

    location /backend/api {
        try_files $uri @proxy_to_asist_backend_api;
    }

    location @proxy_to_asist_backend_api {
        proxy_pass http://asist_backend_api;
        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;
        proxy_set_header X-Forwarded-Proto $scheme;
    }
}


Может еще кто посоветует, насколько socketio лучше channels в случае если сервер синхронный, но требуется двунаправленное общение по протоколу websocket. Обновление библиотеки django-socketio (https://pypi.org/project/django-socketio/) датируется аж 2014 годом, что страшно, честно говоря. Буду рад, если кто поделится мнением и опытом.
  • Вопрос задан
  • 36 просмотров
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Войти через центр авторизации
Похожие вопросы