WebSocket介绍
概念
WebSocket 是 HTML5 开始提供的一种在单个 TCP 连接上进行全双工通讯的协议。
在 WebSocket API 中,浏览器和服务器只需要做一个握手的动作,然后,浏览器和服务器之间就形成了一条快速通道。两者之间就直接可以数据互相传送。
浏览器通过 JavaScript 向服务器发出建立 WebSocket 连接的请求,连接建立以后,客户端和服务器端就可以通过 TCP 连接直接交换数据。
当你获取 Web Socket 连接后,你可以通过 send()方法来向服务器发送数据,并通过 onmessage 事件来接收服务器返回的数据。
WebSocket实现长连接
连接保持 - Http 发起请求再请求中写一个协议 - WebSocket - 服务器收到Websocket请求 ,自动保持此连接 - 永久不断开,除非主动断开 - 可以通过此连接主动找到客户端
使用方法:
按照第三方包
pip3 install gevent-websocket
导入
from geventwebsocket.handler import WebSocketHandler # 提供WS协议处理 from geventwebsocket.server import WSGIServer # 承载服务 from geventwebsocket.websocket import WebSocket # 语法提示
启动
if __name__ == '__main__': http_serve = WSGIServer(('0.0.0.0', 9527), app, handler_class=WebSocketHandler) http_serve.serve_forever()
不再是之前的app.run()了。
后端操作
user_socket = request.environ.get("wsgi.websocket") # type:WebSocket # 这里的# type:WebSocket就是让这个user_socket有WebSocket语法提示 msg = user_socket.receive() # 接收数据 print(msg)
前端操作(JavaScript)
var ws = new WebSocket("ws://127.0.0.1:9527/my_socket"); // 定义WebSocket连接请求 ws.onmessage = function (eventMessage) { console.log(eventMessage.data); };
基于WebSocket的实例
群聊(无昵称)
from flask import Flask, request, render_template from geventwebsocket.handler import WebSocketHandler # 提供WS协议处理 from geventwebsocket.server import WSGIServer # 承载服务 from geventwebsocket.websocket import WebSocket # 语法提示 app = Flask(__name__) user_socket_list = [] @app.route("/my_socket") def my_socket(): user_socket = request.environ.get("wsgi.websocket") # type:WebSocket if user_socket: user_socket_list.append(user_socket) print(len(user_socket_list), user_socket_list) while True: msg = user_socket.receive() print(msg) for u_socket in user_socket_list: try: u_socket.send(msg) except: continue @app.route('/group_chat') def group_chat(): return render_template('群聊.html') if __name__ == '__main__': http_serve = WSGIServer(('0.0.0.0', 9527), app, handler_class=WebSocketHandler) http_serve.serve_forever()
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>群聊</title> </head> <body> <input type="text" id="content"> <button onclick="send_msg()">提交</button> <div id="chat_list"></div> <script type="application/javascript"> var ws = new WebSocket("ws://127.0.0.1:9527/my_socket"); ws.onmessage = function (eventMessage) { console.log(eventMessage.data); var p = document.createElement('p'); p.innerText = eventMessage.data; document.getElementById('chat_list').appendChild(p); }; function send_msg() { var content = document.getElementById('content').value; ws.send(content); } </script> </body> </html>
群聊(有昵称)
from flask import Flask, request, render_template from geventwebsocket.handler import WebSocketHandler from geventwebsocket.server import WSGIServer from geventwebsocket.websocket import WebSocket app = Flask(__name__) user_socket_dict = {} @app.route("/my_socket/<username>") def my_socket(username): user_socket = request.environ.get("wsgi.websocket") # type:WebSocket if user_socket: user_socket_dict[username] = user_socket print(len(user_socket_dict), user_socket_dict) while True: msg = user_socket.receive() print(msg) for u_socket in user_socket_dict.values(): print(user_socket) try: u_socket.send(msg) except: continue @app.route('/group_chat') def group_chat(): return render_template('有昵称的群聊.html') if __name__ == '__main__': http_serve = WSGIServer(('0.0.0.0', 9527), app, handler_class=WebSocketHandler) http_serve.serve_forever()
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>昵称群聊</title> </head> <body> 设置昵称:<input type="text" id="username"> <button onclick="loginGc()">确定</button> <br> <input type="text" id="content"> <button onclick="sendMsg()">提交</button> <div id="chat_list"></div> <script type="application/javascript"> var ws = null; function loginGc() { var username = document.getElementById('username').value; ws = new WebSocket("ws://192.168.16.35:9527/my_socket/" + username); ws.onmessage = function (eventMessage) { console.log(eventMessage.data); str_obj = JSON.parse(eventMessage.data); var p = document.createElement('p'); p.innerText = str_obj.from_user + " : " + str_obj.chat; document.getElementById('chat_list').appendChild(p); }; } function sendMsg() { var username = document.getElementById('username').value; var content = document.getElementById('content').value; var sendStr = { from_user: username, chat: content }; ws.send(JSON.stringify(sendStr)); } </script> </body> </html>
私聊
import json from flask import Flask, request, render_template from geventwebsocket.handler import WebSocketHandler from geventwebsocket.server import WSGIServer from geventwebsocket.websocket import WebSocket app = Flask(__name__) user_socket_dict = {} @app.route("/my_socket/<username>") def my_socket(username): user_socket = request.environ.get("wsgi.websocket") # type:WebSocket if user_socket: user_socket_dict[username] = user_socket print(len(user_socket_dict), user_socket_dict) while True: msg = json.loads(user_socket.receive()) to_user_nick = msg.get('to_user') to_user_socket = user_socket_dict.get(to_user_nick) to_user_socket.send(json.dumps(msg)) @app.route('/sl') def sl(): return render_template('私聊.html') if __name__ == '__main__': http_serve = WSGIServer(('0.0.0.0', 9527), app, handler_class=WebSocketHandler) http_serve.serve_forever()
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>私聊</title> </head> <body> 设置昵称:<input type="text" id="username"> <button onclick="loginGc()">确定</button> <br> 给<input type="text" id="to_user">发送<input type="text" id="content"> <button onclick="sendMsg()">发送</button> <div id="chat_list"></div> <script type="application/javascript"> var ws = null; function loginGc() { var username = document.getElementById('username').value; ws = new WebSocket("ws://192.168.16.35:9527/my_socket/" + username); ws.onmessage = function (eventMessage) { console.log(eventMessage.data); str_obj = JSON.parse(eventMessage.data); var p = document.createElement('p'); p.innerText = str_obj.from_user + " : " + str_obj.chat; document.getElementById('chat_list').appendChild(p); }; } function sendMsg() { var username = document.getElementById('username').value; var to_user = document.getElementById('to_user').value; var content = document.getElementById('content').value; var sendStr = { from_user: username, to_user: to_user, chat: content }; ws.send(JSON.stringify(sendStr)); } </script> </body> </html>