我是使用boost.asio的新手,但我想設計一個簡單的例程來從URL獲取數據並將其保存到內存緩衝區。根據一個例子,我發現,我想出了以下內容:Boost.asio socket - 爲什麼沒有可用的字節
//data_url.hpp
#include <boost/asio.hpp>
#include <string>
#include <vector>
struct data {
data();
boost::asio::io_service io_service;
boost::asio::ip::tcp::resolver resolver;
boost::asio::ip::tcp::socket socket;
std::vector<char> buffer;
std::string host;
std::string path;
std::string port;
};
void setup_url(std::string hst,
std::string pth,
std::string prt = "80");
std::vector<char> & get_data_from_url();
void resolve_handler(const boost::system::error_code & ec,
boost::asio::ip::tcp::resolver::iterator it);
void connect_handler(const boost::system::error_code & ec);
void read_handler(const boost::system::error_code & ec,
std::size_t bytes_transferred);
實施
//data_url.cpp
#include <data_url.hpp>
#include <iostream>
data::data() : io_service(), resolver(io_service), socket(io_service)
, buffer(), host(), path(), port() {}
data d;
void setup_url(std::string hst, std::string pth, std::string prt) {
d.host = hst;
d.path = pth;
d.port = prt;
}
std::vector<char> & get_data_from_url() {
boost::asio::ip::tcp::resolver::query query(d.host, d.port);
d.resolver.async_resolve(query, resolve_handler);
d.io_service.run();
return d.buffer;
}
void resolve_handler(const boost::system::error_code & ec,
boost::asio::ip::tcp::resolver::iterator it) {
if(!ec) {
d.socket.async_connect(*it, connect_handler);
}
}
void connect_handler(const boost::system::error_code & ec) {
if(!ec) {
boost::asio::write(d.socket,
boost::asio::buffer(std::string("GET ") +
std::string(d.path) +
std::string(" HTTP 1.1\r\n") +
std::string("Host: ") +
std::string(d.host) +
std::string("\r\n\r\n")));
boost::system::error_code ec_avail;
d.buffer.resize(d.socket.available(ec_avail));
d.socket.async_read_some(boost::asio::buffer(d.buffer),
read_handler);
}
}
void read_handler(const boost::system::error_code & ec,
std::size_t bytes_transferred) {
if(!ec) {
d.socket.async_read_some(boost::asio::buffer(d.buffer),
read_handler);
}
}
然後,我
#include <data_url.hpp>
int main(int argc, char *argv[]) {
setup_url("www.boost.org", "/");
std::vector<char> data;
data = get_data_from_url();
return 0;
}
該代碼調用read_handler不休,並永遠不會終止運行。我用不同的頁面嘗試過,並沒有什麼區別。
此外,在content_handler
函數中,我使用socket.available()
調整矢量大小。這是爲了使代碼儘可能通用,以便我可以閱讀任何頁面而不必知道它的大小。但是,當我撥打socket.available()
時,它將返回零並將ec_avail
中的錯誤代碼設置爲「未定義的錯誤」。
正如我所提到的,我是使用boost.asio的新手,顯然我在這裏錯過了一些東西。我很感謝幫助解決這些錯誤和任何其他建議/建議。
這是很棒的信息。非常感謝。我會看看波科。 –