使用 Python 实现 WebSocket 服务器与客户端通信

ops/2024/12/20 6:18:46/

简介

WebSocket 是一种基于 TCP 协议的通信协议,能够在客户端与服务器之间进行全双工(双向)通信。相比传统的 HTTP 协议,WebSocket 可以实现实时数据的传输,尤其适合需要实时交互的应用场景,如在线游戏、实时聊天、金融交易等。

我通过 Python 实现一个简单的 WebSocket 服务器,并使其与客户端进行通信。我们将创建两个 Python 文件:websocket.pymain.pywebsocket.py 负责实现 WebSocket 服务器的功能,main.py 负责启动和管理服务器,以及定时向客户端发送消息。

安装 WebSocket 库

在开始之前,需要安装 websockets 库,它是 Python 中非常流行的 WebSocket 实现。

python">pip install websockets

websocketpy__WebSocket__12">websocket.py — WebSocket 服务器实现

websocket.py 文件中,我定义了一个 WebSocketServer 类,包含了 WebSocket 服务器的主要逻辑。

代码解析
python">import asyncio
import websocketsclass WebSocketServer:def __init__(self, host="localhost", port=8765):self.host = hostself.port = portself.clients = set()  # 存储所有连接的客户端

首先,我创建了一个 WebSocketServer 类,它的构造方法初始化了服务器的主机地址 host 和端口号 port,同时维护了一个客户端集合 clients 来存储当前连接的 WebSocket 客户端。

python">    async def handle_client(self, websocket):# 新的客户端连接self.clients.add(websocket)try:async for message in websocket:print(f"收到消息: {message}")# 回显消息给客户端await websocket.send(f"服务器已收到: {message}")except websockets.ConnectionClosed as e:print(f"客户端断开连接: {e}")finally:# 移除断开的客户端self.clients.remove(websocket)

handle_client 是一个异步方法,用来处理与客户端的连接。在客户端发送消息时,服务器会接收到该消息,并通过 websocket.send() 方法将回显消息发送给客户端。如果客户端断开连接,捕获到 ConnectionClosed 异常,并从 clients 集合中移除该客户端。

python">    async def send(self, message):"""向所有连接的客户端发送消息"""if not self.clients:print("没有客户端连接,无法发送消息")returndisconnected_clients = set()for client in self.clients:try:await client.send(message)except websockets.ConnectionClosed:disconnected_clients.add(client)# 清理已断开的客户端self.clients -= disconnected_clients

send 方法允许服务器向所有连接的客户端发送消息。如果有客户端断开连接,服务器会将其从 clients 集合中移除。

python">    async def start(self):print(f"启动 WebSocket 服务器: ws://{self.host}:{self.port}")async with websockets.serve(self.handle_client, self.host, self.port):await asyncio.Future()  # 持续运行直到手动停止

start 方法启动 WebSocket 服务器,通过 websockets.serve() 启动一个 WebSocket 服务,该服务会监听来自客户端的连接请求,并调用 handle_client 方法处理这些请求。await asyncio.Future() 会让服务器持续运行,直到手动停止。

main.py — 启动 WebSocket 服务器并定时发送消息

main.py 文件中,创建了一个 WebSocket 服务器的实例,并启动了一个定时任务,定期向连接的客户端发送消息。

代码解析
python">import asyncio
from websocket import WebSocketServerasync def main():# 创建 WebSocket 服务器实例websocket_server = WebSocketServer()websocket_task = asyncio.create_task(websocket_server.start())  # 启动 WebSocket 服务器

main() 函数中,首先创建了 WebSocketServer 的实例,并启动了 WebSocket 服务器。

python">    # 定时向 WebSocket 客户端发送数据async def send_data_periodically():while True:await asyncio.sleep(5)  # 每 5 秒发送一次数据await websocket_server.send("服务器定时发送消息:ping")

send_data_periodically 是一个定时任务,每隔 5 秒就向所有连接的客户端发送一次 "服务器定时发送消息:ping"

python">    periodic_task = asyncio.create_task(send_data_periodically())# 并发运行所有任务await asyncio.gather(websocket_task, periodic_task)

通过 asyncio.create_task() 启动了定时任务,并通过 asyncio.gather() 并发运行 WebSocket 服务器和定时发送消息的任务。

python">if __name__ == "__main__":asyncio.run(main())

最后,我们 asyncio.run(main()) 启动了整个程序。

总结

通过这两个文件,实现了一个简单的 WebSocket 服务器,该服务器能够接收客户端消息并进行回显。同时,服务器也能够定时向所有连接的客户端发送消息。

完整代码

websocket.py

python">import asyncio
import websocketsclass WebSocketServer:def __init__(self, host="localhost", port=8765):self.host = hostself.port = portself.clients = set()  # 存储所有连接的客户端async def handle_client(self, websocket):# 新的客户端连接self.clients.add(websocket)try:async for message in websocket:print(f"收到消息: {message}")# 回显消息给客户端await websocket.send(f"服务器已收到: {message}")except websockets.ConnectionClosed as e:print(f"客户端断开连接: {e}")finally:# 移除断开的客户端self.clients.remove(websocket)async def send(self, message):"""向所有连接的客户端发送消息"""if not self.clients:print("没有客户端连接,无法发送消息")returndisconnected_clients = set()for client in self.clients:try:await client.send(message)except websockets.ConnectionClosed:disconnected_clients.add(client)# 清理已断开的客户端self.clients -= disconnected_clientsasync def start(self):print(f"启动 WebSocket 服务器: ws://{self.host}:{self.port}")async with websockets.serve(self.handle_client, self.host, self.port):await asyncio.Future()  # 持续运行直到手动停止

main.py

python">import asyncio
from websocket import WebSocketServerasync def main():# 创建 WebSocket 服务器实例websocket_server = WebSocketServer()websocket_task = asyncio.create_task(websocket_server.start())  # 启动 WebSocket 服务器# 定时向 WebSocket 客户端发送数据async def send_data_periodically():while True:await asyncio.sleep(5)  # 每 5 秒发送一次数据await websocket_server.send("服务器定时发送消息:ping")periodic_task = asyncio.create_task(send_data_periodically())# 并发运行所有任务await asyncio.gather(websocket_task, periodic_task)if __name__ == "__main__":asyncio.run(main())

http://www.ppmy.cn/ops/143401.html

相关文章

3D目标检测数据集及评价指标

1. KITTI 一个前视双目数据集,附有雷达数据,主要用于单目3D目标检测模型。数据集根据遮挡将目标分为三档,分别是未遮挡Easy,半遮挡Mod.,和大部分遮挡Hard,一般模型检测指标都是根据这三类标签分别计算mAP。…

HCIE-day7

三层路由 当路由器(或者其他三层设备)收到一个IP数据包时,路由器会找出报文中的IP头里的目的IP地址,然后根据目的IP地址在自己的路由表(routing table)中进行查询,找到匹配的路由条目之后&…

GIT区域介绍及码云+GIt配置仓库

GIT区域介绍 创建文件夹git init 1、git有3个区域 工作区(working directory):项目的根目录,不包 括.git在内的其他文件暂存区(stage area):是一个看不见的区域,git add 命令就是将文…

设计模式——单例模式(饿汉式,懒汉式等)

设计模式——单例模式(饿汉式,懒汉式等) 目录 设计模式——单例模式(饿汉式,懒汉式等)概念核心要点实现基础要点饿汉式懒汉式懒汉式(线程安全,双重检查锁定)静态内部类实…

利用Python爬虫获取淘宝店铺详情

在数字化时代,数据已成为企业最宝贵的资产之一。对于电商平台,尤其是淘宝这样的大型电商平台,店铺详情数据的获取和分析对于商家来说至关重要。它不仅可以帮助商家了解市场趋势,还可以优化营销策略,提升销售业绩。本文…

powershell(1)

免责声明 学习视频来自 B 站up主泷羽sec,如涉及侵权马上删除文章。 笔记的只是方便各位师傅学习知识,以下代码、网站只涉及学习内容,其他的都与本人无关,切莫逾越法律红线,否则后果自负。 泷羽sec官网:http…

数据结构-树(二叉树)

在了解树具体的代码实现之前,先了解一下树的基础知识: 根节点:第一个结点;叶子节点(终端节点):之后再没有其它结点的结点;分支节点(非终端节点):…

【数值特性库】入口文件

数值特性库入口文件为lib.rs。该文件定义一系列数字特性的trait(特征),这些特性可以被不同的数字类型实现,从而提供一套通用的数值操作方法。下面是对代码中关键部分的解释: 一、基础设置 #![doc(html_root_url “h…