Channels
В директории приложения chat создайте файл consumers.py для потребителей, который будет обрабатывать подключение через веб-сокет от клиента.
Добавьте в файл consumers.py следующий код:
from channels.generic.websocket import WebsocketConsumer
class JoinAndLeave(WebsocketConsumer):
def connect(self):
print("server says connected")
def receive(self, text_data=None, bytes_data=None):
print("server says client message received: ", text_data)
self.send("Server sends Welcome")
def disconnect(self, code):
print("server says disconnected")
Класс потребителя может быть либо синхронным, либо асинхронным, либо и тем, и другим. Класс потребителя, который вы создали выше, наследуется от класса WebsocketConsumer, который позволяет вам писать ваш потребитель в синхронном коде и заботится об асинхронных операциях в фоновом режиме.
Созданный вами потребительский класс имеет методы connect, receive и disconnect, которые в настоящее время просто выводят на терминал сообщения о полученном событии:
- Метод
connectобрабатывает запрос клиентаHandshake. - Метод
receiveобрабатывает любое сообщение, отправленное на сервер из метода отправки клиентского API веб-сокета. - Метод
disconnectэквивалентен методу клиентаonclose.
Следующим шагом является создание маршрута веб-сокета, который будет вызывать JoinAndLeave потребителя.
Создайте файл routing.py в директории приложения chat и добавьте в него следующий код:
from django.urls import re_path, path
from . import consumers
websocket_urlpatterns = [
path('', consumers.JoinAndLeave.as_asgi())
]
- Метод
.as_asgi()преобразует класс в приложение ASGI и похож на.as_view()в классах Django.
На данный момент у вас есть два разных веб-протокола с разными маршрутами: протокол HTTP и протокол веб-сокета.
Вам нужно создать маршрутизатор протокола, чтобы сервер ASGI мог знать, как маршрутизировать эти разные протоколы.
Пакет Channels предоставляет класс ProtocolTypeRouter, который может сделать это за нас.
Измените файл asgi.py, как показано ниже:
import os
from channels.routing import ProtocolTypeRouter, URLRouter
from django.core.asgi import get_asgi_application
import chat.routing
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'django_channels_chat.settings')
asgi_application = get_asgi_application() #new
application = ProtocolTypeRouter({
"http": asgi_application,
"websocket": URLRouter(chat.routing.websocket_urlpatterns)
})
Внутри ProtocolTypeRouter вы указали протокол, который хотите маршрутизировать, как объект словаря, который имеет ключ протокола и значение приложения протокола.
get_asgi_application() работает только с протоколом HTTP.
Вы указали URL-маршрутизаторы для протокола веб-сокетов, используя класс URLRouter, в который вы передали список шаблонов веб-сокетов, созданных ранее.