django中配置使用websocket终极解决方案

django ASGI/Channels 启动和 ASGI/daphne的区别

Django ASGI/Channels 是 Django 框架的一个扩展,它提供了异步服务器网关接口(ASGI)协议的支持,以便处理实时应用程序的并发连接。ASGI 是一个用于构建异步 Web 服务器和应用程序的规范。

在以前的版本中,Django 使用的是 WSGI(Web 服务器网关接口)协议,该协议是一种同步的协议,只能处理一个请求-响应周期。这意味着在处理长轮询、WebSocket 及其他类似的实时应用程序时,传统的 Django 无法提供良好的性能和扩展性。

与传统的 Django 不同,使用 Django ASGI/Channels 可以构建具有实时功能的异步应用程序,例如聊天应用、通知系统等。Channels 提供了一个消息队列来处理异步任务,并且可以与 WebSocket、长轮询等技术结合使用。

ASGI/daphne 是一个符合 ASGI 规范的异步 Web 服务器,能够处理 ASGI 应用程序的并发连接。它是 Channels 官方推荐的生产级服务器,并提供高性能和可靠的连接管理。你可以将 ASGI/daphne 与 Django ASGI/Channels 一起使用,以部署具有实时功能的 Django 应用程序。

总结来说,Django ASGI/Channels 是 Django 的一个扩展,使其能够处理实时应用程序的并发连接。而 ASGI/daphne 则是一个符合 ASGI 规范的异步 Web 服务器,用于处理 ASGI 应用程序的并发连接。两者结合使用可以构建高性能、具有实时功能的 Django 应用程序。

文件类比

daphne 启动命令

daphne 你的工程项目名称.asgi:application

python本身只支持http协议 使用websocket需要下载第三方库

pip install -U channels

需要在seting.py里配置,将我们的channels加入INSTALLED_APP里。

INSTALLED_APPS = (

'django.contrib.auth',

'django.contrib.contenttypes',

'django.contrib.sessions',

'django.contrib.sites',

...

'channels',

)

尾行添加

ASGI_APPLICATION = 'bug_Project_name.asgi.application'

修改asgi.py文件

import os

from channels.routing import ProtocolTypeRouter,URLRouter

from django.core.asgi import get_asgi_application

from . import routing

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

#application = get_asgi_application()

application = ProtocolTypeRouter({

"http":get_asgi_application(),

"websocket":URLRouter(routing.websoctet_urlpatterns )

})

在settings.py的同级目录创建routing.py

from django.urls import re_path

from web import consumers

websoctet_urlpatterns = [

re_path('ws/(?P<group>\w+)/$',consumers.ChatConsumer.as_asgi()),

]

在web.views中创建consumers.py

-*- coding:UTF-8 -*-

author:Administrator

contact: 913632472@qq.com

datetime:2022/1/10 11:55

software: PyCharm

"""

文件说明:

"""

from channels.generic.websocket import WebsocketConsumer

from channels.exceptions import StopConsumer

class ChatConsumer(WebsocketConsumer):

def websocket_connect(self,message):

有客户端来向后端发送websocket连接请求时,自动触发

后端允许客户端创建连接

print('有人来了')

self.accept()

#给客户端发送小时

self.send("欢迎啊")

def websocket_receive(self, message):

浏览器基于websocket向后端发送数据,自动触发接受消息

text = message['text']

print("接受到消息-->", text)

res = "{}SB".format(text)

if text == "关闭":

客户端通过发送命令 主动断开连接

self.close()

print('通过命令关闭')

raise StopConsumer # 如果服务端断开连接,执行StopConsumer异常 那么websocket_disconnect不会执行

self.send(res)

self.close() #后端主动断开websocket

def websocket_disconnect(self, message):

客户端与服务端断开连接,自动触发

print("客户端断开连接")

raise StopConsumer

django中需要了解的

  • wsgi,只支持http请求
  • asgi,wsgi+异步+websockt

settings.py的installed_apps中的首行

简单使用前端页面测试websocket

<html lang="en">

<head>

<meta charset="UTF-16">

<title>title</title>

<style>

.message{

height: 300px;

border: 1px solid #dddddd;

width: 100%;

}

</style>

</head>

</html>

<div class="message" id="message"></div>

<div>

<input type="text" placeholder="请输入" id="txt">

<input type="button" value="发送" οnclick="sendMessage()">

</div>

<script>

socket = new WebSocket("ws://127.0.0.1:8000/room/123/")

//创建好连接后触发

socket.onopen = function (event) {

let tag = document.createElement("div");

tag.innerText = "[连接成功]";

document.getElementById("message").appendChild(tag);

}

//当websocket接受要服务端发来的信息 会自动触发这个函数

socket.onmessage = function (event){

let tag = document.createElement("div");

tag.innerText = event.data;

document.getElementById("message").appendChild(tag);

}

function sendMessage(){

let tag = document.getElementById("txt");

socket.send(tag.value);

}

function closeConn() {

socket.close(); //服务端发送断开请求

}

</script>

websocket介绍:

channels 4.0之后默认不带Daphne服务器了。

解决方案可以有两种:
1.指定channels的版本为3.x;
2.安装时使用pip3 install -U channels["daphne"]

当前问题不管高版本还是低版本 老是报如下问题

之后找到老师获取课程中的源代码 笔者使用教程中的代码跑通了

还是回到这个问题

这个坑废了我2天时间

ValueError: No application configured for scope type 'websocket'

经过课程中的代码和笔者的代码来回对比 多次测试

这里应该是websocket 而缺少了e字母 应该是写项目的时候复制csdn参考源码 网友留的坑

而后将项目依赖全部升级为最新版本 完全可以跑通!

效果图

小结

基于django实现websocket请求 但只能对某个人进行处理

群聊(二)

基于channels中提供channel layers来实现。

  • setting中配置。

    复制代码
    CHANNEL_LAYERS = {
        "default": {
            "BACKEND": "channels.layers.InMemoryChannelLayer",
        }
    }
    复制代码
    pip3 install channels-redis
    复制代码
    CHANNEL_LAYERS = {
        "default": {
            "BACKEND": "channels_redis.core.RedisChannelLayer",
            "CONFIG": {
                "hosts": [('10.211.55.25', 6379)]
            },
        },
    }
  • consumers中特殊的代码。

    复制代码
    from channels.generic.websocket import WebsocketConsumer
    from channels.exceptions import StopConsumer
    from asgiref.sync import async_to_sync
    ​
    ​
    class ChatConsumer(WebsocketConsumer):
        def websocket_connect(self, message):
            # 接收这个客户端的连接
            self.accept()
    ​
            # 获取群号,获取路由匹配中的
            group = self.scope['url_route']['kwargs'].get("group")
    ​
            # 将这个客户端的连接对象加入到某个地方(内存 or redis)
            async_to_sync(self.channel_layer.group_add)(group, self.channel_name)
    ​
        def websocket_receive(self, message):
            group = self.scope['url_route']['kwargs'].get("group")
    ​
            # 通知组内的所有客户端,执行 xx_oo 方法,在此方法中自己可以去定义任意的功能。
            async_to_sync(self.channel_layer.group_send)(group, {"type": "xx.oo", 'message': message})
    ​
        def xx_oo(self, event):
            text = event['message']['text']
            self.send(text)
    ​
        def websocket_disconnect(self, message):
            group = self.scope['url_route']['kwargs'].get("group")
    ​
            async_to_sync(self.channel_layer.group_discard)(group, self.channel_name)
            raise StopConsumer()
    ​

总结

b站演示地址 [​ https://b23.tv/UZvBFy3 ​]( "​ https://b23.tv/UZvBFy3 ​")

  • websocket是什么?协议。

  • django中实现websocket,channels组件。

    • 单独连接和收发数据。

    • 手动创建列表 & channel layers。

【全网最详细Django的websocket 通信原理,聊天室,实战案例-哔哩哔哩】http://​ https://b23.tv/os2enKj ​

参考链接http://t.csdn.cn/RyrcC

备用链接django中配置websocket_基于wsgi创建的项目怎么实现websocket_qq_36606793的博客-CSDN博客

相关推荐
ROBOT玲玉34 分钟前
Milvus 中,FieldSchema 的 dim 参数和索引参数中的 “nlist“ 的区别
python·机器学习·numpy
小_太_阳1 小时前
Scala_【1】概述
开发语言·后端·scala·intellij-idea
智慧老师1 小时前
Spring基础分析13-Spring Security框架
java·后端·spring
Kai HVZ1 小时前
python爬虫----爬取视频实战
爬虫·python·音视频
古希腊掌管学习的神1 小时前
[LeetCode-Python版]相向双指针——611. 有效三角形的个数
开发语言·python·leetcode
m0_748244832 小时前
StarRocks 排查单副本表
大数据·数据库·python
B站计算机毕业设计超人2 小时前
计算机毕业设计PySpark+Hadoop中国城市交通分析与预测 Python交通预测 Python交通可视化 客流量预测 交通大数据 机器学习 深度学习
大数据·人工智能·爬虫·python·机器学习·课程设计·数据可视化
路人甲ing..2 小时前
jupyter切换内核方法配置问题总结
chrome·python·jupyter
游客5202 小时前
opencv中的常用的100个API
图像处理·人工智能·python·opencv·计算机视觉
每天都要学信号2 小时前
Python(第一天)
开发语言·python