概述
在使用python+websocket部署socket服务,前端使用小程序来连接,过程中存在以下可能出现的问题:
1,代码里socket端口问题2,服务器配置问题(域名解析?Nginx配置是否正确处理了WebSocket升级头?)3,小程序端口配置错误(是否是443:wss://example.com:443)
1,代码里socket端口问题
代码里端口设置为:8765。特别要留意端口是否在安全组里添加入站规则,在服务器面板中添加:
# coding: utf-8
import asyncio
import json
import logging
import websockets
from datetime import datetime
from threading import Thread
import time# 全局变量存储所有连接的客户端
connected_clients = {}async def handle_message(websocket, message):"""处理客户端消息"""try:data = json.loads(message)action = data.get("action")if action == "login":# 用户登录user_id = data["user_id"]connected_clients[user_id] = websocketawait broadcast_system_message(f"用户 {user_id} 上线了")print(f"用户 {user_id} 已连接")elif action == "chat":# 聊天消息sender = data["user_id"]content = data["content"]target = data.get("target")if target: # 私聊await send_private_message(sender, target, content)else: # 群发await broadcast_message(sender, content)except Exception as e:print(f"消息处理错误: {e}")async def send_private_message(sender, target, content):"""发送私聊消息"""if target in connected_clients:message = {"type": "private","from": sender,"content": content,"time": datetime.now().strftime("%H:%M:%S")}await connected_clients[target].send(json.dumps(message))print(f"私聊消息: {sender} -> {target}: {content}")async def broadcast_message(sender, content):"""广播消息给所有用户"""message = {"type": "public","from": sender,"content": content,"time": datetime.now().strftime("%H:%M:%S")}for user_id, client in connected_clients.items():if client.open:await client.send(json.dumps(message))print(f"广播消息: {sender}: {content}")async def broadcast_system_message(content):"""发送系统通知"""message = {"type": "system","content": content,"time": datetime.now().strftime("%H:%M:%S")}for user_id, client in connected_clients.items():if client.open:await client.send(json.dumps(message))async def handle_connection(websocket, path):"""处理新连接"""user_id = Nonetry:async for message in websocket:await handle_message(websocket, message)except websockets.exceptions.ConnectionClosed:passfinally:if user_id in connected_clients:del connected_clients[user_id]await broadcast_system_message(f"用户 {user_id} 下线了")print(f"用户 {user_id} 已断开")async def health_check():"""心跳检测(每30秒清理死连接)"""while True:await asyncio.sleep(30)dead_clients = [user_id for user_id, client in connected_clients.items()if not client.open]for user_id in dead_clients:del connected_clients[user_id]async def main():startup_time = datetime.now().strftime("%Y-%m-%d %H:%M:%S")print(f"【服务启动】Chat Server 启动时间: {startup_time}")# 启动心跳检测asyncio.create_task(health_check())# 启动WebSocket服务器server = await websockets.serve(handle_connection,"0.0.0.0", # 监听所有IP8765, # 端口ping_interval=None # 禁用自动ping(手动实现心跳))print("聊天服务器已启动,等待连接...")await server.wait_closed()if __name__ == "__main__":asyncio.run(main())
2,服务器配置问题
①直接访问地址(chat.y***.cn),发现不能访问,首先考虑域名解析问题,添加域名解析:
②项目使用Nginx反向代理,检查Nginx配置是否正确处理了WebSocket升级头,查看网站配置,添加内容:
location / {proxy_pass http://localhost:8765;proxy_http_version 1.1;proxy_set_header Upgrade $http_upgrade;proxy_set_header Connection "upgrade";proxy_set_header Host $host;proxy_set_header X-Real-IP $remote_addr;proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;}
3,小程序端口配置错误(是否是443:wss://example.com:443)
这个容易犯的低级错误,端口直接填写了8765。
4,前端测试代码
wx.connectSocket({url: 'wss://chat.*****.cn:443',success: () => console.log('连接成功'),fail: (err) => console.error('连接失败', err)})
输出:连接成功