Вопрос

I am currently trying to figure out how to properly reuse an asio socket. I am able to successfully send out a request, and get the result. The second time I send out a request, I get an exception: read_some: End of file. The second write seems to work fine, I see the second http request going out over wireshark. I am thinking that there is left over information on the socket that is corrupting my connection in some way. Any help would be appreciated with this issue. Here is the code I am using:

persistent_connection::persistent_connection(std::string ip, std::string port):
io_service_(), socket_(io_service_), is_setup_(false)
{
    boost::asio::ip::tcp::resolver resolver(io_service_);
    boost::asio::ip::tcp::resolver::query query(ip,port);
    boost::asio::ip::tcp::resolver::iterator iterator = resolver.resolve(query);
    boost::asio::ip::tcp::endpoint endpoint = *iterator;
    socket_.async_connect(endpoint, boost::bind(&persistent_connection::handler_connect, this, boost::asio::placeholders::error, iterator));
    io_service_.run();
}


void persistent_connection::handler_connect(const boost::system::error_code &ec, boost::asio::ip::tcp::resolver::iterator endpoint_iterator)
{
    if(ec)
    {
        std::cout << "Couldn't connect" << ec << std::endl;
        return;
    }
    else
    {
        boost::asio::socket_base::keep_alive keep_option(true);
        socket_.set_option(keep_option);
    }
}


void persistent_connection::write(std::string message)
{
    std::string request_stream = "GET /" + message + " HTTP/1.0\r\n";
    request_stream += "HOST: 10.1.10.220";
    request_stream += "Accept: */*\r\n";
    request_stream += "Connection: keep-alive\r\n\r\n";

    try
    {
        boost::asio::write(socket_, boost::asio::buffer(request_stream, request_stream.size()));
    }catch(std::exception& e)
    {
        std::cout << "Write exception: " << e.what() << std::endl;
    }

    boost::array<char,8192> buf;
    try
    {
        socket_.read_some(boost::asio::buffer(buf));
    }catch(std::exception& e)
    {
        std::cout << "Read exception: " << e.what() << std::endl;
    }

    std::string response = buf.data();
    std::cout << response << std::endl;
}

Edit: Added main function.

int main()
{
    persistent_connection p("10.1.10.220", "80");
    std::string check;
    do
    {
        std::cin >> check;
        if(check.compare("s") == 0)
        {
            std::cout << "Sending" << std::endl;
            p.write("100");
        }
    }while(check.compare("x") != 0);
}
Это было полезно?

Решение

The fact you get this exception when trying to read_some means that the HTTP server closes the connection after the first request is over, i.e. the server ignores "Connection: keep-alive" header (note that HTTP 1.0 servers don't necessarily support persistent connections).

However, in 1.1 version connections are persistent by default, so requesting "HTTP/1.1" should solve this issue.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top