C++ websocket通信
参考 https://blog.csdn.net/qq_67582098/article/details/149980479
为了将前端程序与后台程序分离,除了使用Restfull API,还可以使用websocekt.
websocket是HTML5与服务端长连接的消息推送机制,是建立在TCP协议之上的。
websocket开源通信库有websocketpp和libwebsocket.
一、websokcetpp
WebSocketpp 是一个跨平台的开源(BSD 许可证)头部专用 C++库,它允许将 WebSocket 客户端和服务器功能集成到 C++程序中。在最常见的配置中,全功能网络 I/O 由 Asio 网络库提供。
WebSocketpp 的主要特性包括:
• 事件驱动的接口
• 支持 HTTP/HTTPS、WS/WSS、IPv6
• 灵活的依赖管理 — Boost 库/C++11 标准库
• 可移植性:Posix/Windows、32/64bit、Intel/ARM
• 线程安全
WebSocketpp 同时支持 HTTP 和 Websocket 两种网络协议, 比较适用于我们本次的项目, 所以我们选用该库作为项目的依赖库用来搭建 HTTP 和 WebSocket 服务器。
1.1 安装websocketpp
sudo apt-get install libboost-dev libboost-system-dev libwebsocketpp-dev
验证安装成功可检查/usr/include/websocketpp/
目录是否存在头文件
1.2 编写测试程序
#include <set>
#include <websocketpp/config/asio_no_tls.hpp>
#include <websocketpp/server.hpp>typedef websocketpp::server<websocketpp::config::asio> server;
using websocketpp::connection_hdl;
using websocketpp::lib::placeholders::_1;
using websocketpp::lib::placeholders::_2;
using websocketpp::lib::bind;class broadcast_server {
public:void on_open(connection_hdl hdl) { m_connections.insert(hdl); }void on_close(connection_hdl hdl) { m_connections.erase(hdl); }void on_message(connection_hdl hdl, server::message_ptr msg) {for(auto conn : m_connections) {m_server.send(conn, msg);}}void run(uint16_t port) {m_server.init_asio();m_server.set_open_handler(bind(&broadcast_server::on_open, this, _1));m_server.set_close_handler(bind(&broadcast_server::on_close, this, _1));m_server.set_message_handler(bind(&broadcast_server::on_message, this, _1, _2));m_server.listen(port);m_server.start_accept();m_server.run();}
private:server m_server;std::set<connection_hdl, std::owner_less<connection_hdl>> m_connections;
};int main() {broadcast_server server;server.run(9002);
}
编译
g++ websocketTest.cpp -std=c++14 -lboost_system -lpthread -o websocketTest
编写HTML测试程序
<!DOCTYPE html>
<html lang="zh-CN">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>WebSocket 通信演示</title><style>body {font-family: 'Segoe UI', sans-serif;max-width: 800px;margin: 0 auto;padding: 20px;}#message-container {height: 400px;border: 1px solid #ddd;border-radius: 8px;padding: 15px;margin-bottom: 20px;overflow-y: auto;background: #f9f9f9;}#message-input {width: 70%;padding: 10px;border: 1px solid #ccc;border-radius: 4px;}button {padding: 10px 15px;background: #4285f4;color: white;border: none;border-radius: 4px;cursor: pointer;margin-left: 10px;}.message {margin: 8px 0;padding: 8px 12px;border-radius: 18px;max-width: 70%;word-wrap: break-word;}.received {background: #e3f2fd;align-self: flex-start;}.sent {background: #4285f4;color: white;align-self: flex-end;margin-left: auto;}</style>
</head>
<body><h1>WebSocket 通信演示</h1><div id="message-container"></div><div><input type="text" id="message-input" placeholder="输入消息..."><button onclick="sendMessage()">发送</button><button onclick="connect()">连接</button><button onclick="disconnect()">断开</button></div><script>let socket;const messageContainer = document.getElementById('message-container');const messageInput = document.getElementById('message-input');function connect() {if (socket && socket.readyState === WebSocket.OPEN) {appendMessage('连接已存在');return;}socket = new WebSocket('ws://192.168.58.129:9002');socket.onopen = () => {appendMessage('已连接到服务器', 'system');};socket.onmessage = (event) => {appendMessage(event.data, 'received');};socket.onclose = () => {appendMessage('连接已关闭', 'system');};socket.onerror = (error) => {appendMessage(`连接错误: ${error.message}`, 'error');};}function sendMessage() {if (!socket || socket.readyState !== WebSocket.OPEN) {appendMessage('请先建立连接', 'error');return;}const message = messageInput.value.trim();if (message) {socket.send(message);appendMessage(message, 'sent');messageInput.value = '';}}function disconnect() {if (socket && socket.readyState === WebSocket.OPEN) {socket.close();}}function appendMessage(message, type = 'received') {const messageElement = document.createElement('div');messageElement.classList.add('message', type);messageElement.textContent = message;messageContainer.appendChild(messageElement);messageContainer.scrollTop = messageContainer.scrollHeight;}// 页面加载时自动连接window.onload = connect;</script>
</body>
</html>
演示效果