我尝试使用 boost::beast::websocket::aysnc_write 进行多次调用,我对缓冲区进行了排队,并在写入结束时,在句柄中,我从队列中弹出并再次调用写入。我尝试通过 5 次调用来运行它,但在弹出第二个缓冲区后它停止运行。
我在1.72.0版本中使用Boost,linux rocky
void Session::do_write(std::string data)
{
std::cout << "do_write" << std::endl;
if (m_isWrite) {
std::cout << "do_write push" << std::endl;
m_queueBufferTx.push(boost::asio::buffer(data));
return;
}
m_bufferTx = boost::asio::buffer(data);
on_write();
}
void Session::on_write()
{
std::cout << "write size " <<m_queueBufferTx.size() << std::endl;
m_isWrite = true;
m_ws.text(m_ws.got_text());
m_ws.async_write(m_bufferTx, beast::bind_front_handler(&Session::handle_write, shared_from_this()));
}
void Session::handle_write(beast::error_code ec, std::size_t bytes_transferred)
{
m_isWrite = false;
std::cout << "finish write size " <<m_queueBufferTx.size() << std::endl;
boost::ignore_unused(bytes_transferred);
if (ec) {
LOGGER(MtLogger::ERROR, "write: " << ec.message() << "\n")
return;
}
if (!m_queueBufferTx.empty() && !m_isWrite) {
std::cout << "handle_write pop" << std::endl;
m_isWrite = true;
m_bufferTx = m_queueBufferTx.pop();
on_write();
}
}
我主要做的是:
json ex = { { "type", "X400FeCmd" }, { "command", "Disconnection"} };
for (int i = 0; i < 5; ++i){
session->do_write(ex.dump());
}
在终端中,我看到打印内容: 做_写
write size 0
do_write
do_write push
do_write
do_write push
do_write
do_write push
do_write
do_write push
finish write size 4
handle_write pop
write size 3
我认为问题隐藏在这两者之间的相互作用中:
if (m_isWrite) {
std::cout << "do_write push" << std::endl;
m_queueBufferTx.push(boost::asio::buffer(data));
return;
}
还有这个:
std::cout << "write size " <<m_queueBufferTx.size() << std::endl;
m_isWrite = true;
当你等待时
m_ws.async_write(m_bufferTx, beast::bind_front_handler(&Session::handle_write, shared_from_this()));
为了完成,你的外循环设法再调用
do_write
4 次。完成处理程序 handle_write
仅在事后执行,此时已经为时已晚。您可以使用例如 boost::asio::deadline_timer
来验证它是否在循环中添加延迟。我不完全理解 m_isWrite
的需要,只需检查你的缓冲区是否有东西并弹出它的内容。