基于websocketpp的简易WebSocket聊天客户端无法发送消息求助
解决WebSocketpp客户端用户输入消息无法发送的问题
看起来问题核心出在事件循环被阻塞上!WebSocketpp是基于异步IO模型的,它的核心io_service(新版本为executor)需要持续运行才能处理所有网络操作——包括消息发送。你的用户输入代码直接在事件循环线程里执行,std::getline会阻塞线程,导致WebSocketpp根本没机会处理发送消息的IO任务,消息只能一直留在缓冲里,直到程序退出都发不出去。而自动发送的代码是在事件循环还没被阻塞时执行的,所以能正常工作。
这里给你具体的解决思路和修改方案:
1. 将用户输入逻辑放到独立线程中
把读取用户输入的代码放到单独线程,避免阻塞事件循环线程。同时,WebSocketpp的对象并非线程安全,跨线程调用send时必须用get_io_service().post()把发送操作包装到事件循环线程中执行。
修改后的代码示例:
// 启动WebSocketpp事件循环到独立线程 std::thread ws_run_thread([&c]() { c->run(); }); std::string input; bool keep_running = true; // 在主线程(或独立输入线程)处理用户输入 do { std::cout << "What should I tell the ws? "; std::getline(std::cin, input); if (input == "exit") { keep_running = false; // 停止WebSocketpp事件循环 c->stop(); } else { // 用post将send操作投递到事件循环线程,保证线程安全 c->get_io_service().post([&c, hdl, input]() { try { c->send(hdl, input, websocketpp::frame::opcode::text); std::cout << "Told ws: " << input << std::endl; } catch (const websocketpp::exception& e) { std::cerr << "Failed to send message: " << e.what() << std::endl; } }); } } while (keep_running); // 等待事件循环线程结束 ws_run_thread.join();
2. 补充错误处理
你原代码没有捕获send可能抛出的异常,添加异常捕获可以帮你排查潜在问题(比如连接断开、hdl失效等)。
3. 确保事件循环持续运行
要保证c->run()所在的线程一直处于运行状态,直到你主动调用c->stop()退出程序,这样WebSocketpp才能持续处理网络IO任务。
总结一下:自动发送的代码能正常工作,是因为它在事件循环未被阻塞时执行,WebSocketpp有机会立即处理发送任务;而用户输入的代码阻塞了线程,事件循环被卡住,所有IO操作都暂停了。
内容的提问来源于stack exchange,提问作者Purefan
相关产品推荐
相关产品推荐

