boost::asio::ip::tcp::socket无法读取任何内容。

3

这实际上是我第一次使用Socket编程,而不是复制粘贴教程代码和玩乐。无论如何,它都不能正常工作。我认为我已经仔细阅读了文档,但可能还不够。我怀疑在read_message()中使用socket::read_some(),因为我的问题程序停在了读取部分。我认为我使用它的方式应该没问题,因为socket::read_some()的文档说明了“函数调用将阻塞,直到成功读取一个或多个字节的数据,或者发生错误。”以下是我的代码。感谢任何帮助。

void read_message(std::string& message, boost::asio::ip::tcp::socket& socket)
{
    std::stringstream message_stream;
    while (true)
    {
        std::array<char, 128> buffer;
        boost::system::error_code error;
        size_t len = socket.read_some(boost::asio::buffer(buffer), error);
        if (error == boost::asio::error::eof)
        {
            break;
        }
        message_stream.write(buffer.data(), len);
    }
    message = message_stream.str();
}

server.cpp

int main()
{
    while (true)
    {
        boost::asio::io_service io_service;
        boost::asio::ip::tcp::acceptor acceptor(io_service, boost::asio::ip::tcp::endpoint(
            boost::asio::ip::tcp::v4(), 9999));
        boost::asio::ip::tcp::socket socket(io_service);
        acceptor.accept(socket);
        std::cout << "connected with client, waiting for a message\n";
        std::string message;
        read_message(message, socket);
        boost::asio::ip::tcp::endpoint endpoint = socket.remote_endpoint();
        std::cout << "message received from " << endpoint.address().to_string() <<
            ':' << endpoint.port() << '\n' << message << '\n';
        boost::asio::write(socket, boost::asio::buffer(message));
        if (message.compare("quit") == 0)
        {
            break;
        }
    }
    return EXIT_SUCCESS;
}

client.cpp

int main()
{
    while (true)
    {
        std::cout << "your message to be sent: ";
        std::string message;
        std::getline(std::cin, message);
        boost::asio::io_service io_service;
        boost::asio::ip::tcp::resolver resolver(io_service);
        boost::asio::ip::tcp::resolver::query query("localhost", "9999");
        boost::asio::ip::tcp::resolver::iterator endpoint_iterator = resolver.resolve(query);
        boost::asio::ip::tcp::socket socket(io_service);
        boost::asio::connect(socket, endpoint_iterator);
        std::cout << "connected to server\n";
        boost::asio::write(socket, boost::asio::buffer(message));
        read_message(message, socket);
        std::cout << "message received from server: " << message << '\n';
        if (message.compare("quit") == 0)
        {
            break;
        }
    }
    return EXIT_SUCCESS;
}
1个回答

3
问题出现在read_message函数中:您读取到eof,但只有当套接字关闭时才会收到eof信号。
也许您的意思是在遇到某个定界符,比如 '\n' 时从read_message函数中返回。然后您可以手动检查缓冲区,或使用read_until函数。
使用read_until函数,read_message将如下所示:
void read_message(std::string& message, boost::asio::ip::tcp::socket& socket)
{
  std::stringstream message_stream;
  boost::asio::streambuf buffer;
  boost::system::error_code error;
  size_t len = read_until(socket, buffer, '\n', error);
  if (len)
  {
    message_stream.write(boost::asio::buffer_cast<const char *>(buffer.data()), len);
    message = message_stream.str();
  }
}

请记得在客户端发送的信息末尾添加'\n':
//...
std::cout << "connected to server\n";
boost::asio::write(socket, boost::asio::buffer(message + '\n'));
read_message(message, socket);
//...

这有点像解析输出,你能否分享一种提取statusCode、message和内容的方法?假设头大小保持不变,但内容大小可能会有所变化。 - CocoCrisp

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接