X-Git-Url: http://git.tdb.fi/?p=libs%2Fnet.git;a=blobdiff_plain;f=source%2Fhttp%2Fclient.cpp;h=6f221810c922a78f85289934b36ce4d6b71b2100;hp=80815e0c9f6c33a5ced29e65cb6c82674c8b8b97;hb=ebbf753626c9e5dd26743c379741c53f9f11866e;hpb=6af1bfce6dc53104c5406adef32d186384525ae3 diff --git a/source/http/client.cpp b/source/http/client.cpp index 80815e0..6f22181 100644 --- a/source/http/client.cpp +++ b/source/http/client.cpp @@ -13,6 +13,9 @@ namespace Http { Client::Client(): sock(0), event_disp(0), + resolver(0), + resolve_listener(0), + resolve_tag(0), user_agent("libmsphttp/0.1"), request(0), response(0) @@ -34,26 +37,26 @@ void Client::use_event_dispatcher(IO::EventDispatcher *ed) event_disp->add(*sock); } +void Client::use_resolver(Net::Resolver *r) +{ + if(resolver) + { + delete resolve_listener; + resolve_listener = 0; + } + + resolver = r; + if(resolver) + resolve_listener = new ResolveListener(*this); +} + void Client::start_request(const Request &r) { if(request) throw client_busy(); - string host = r.get_header("Host"); - if(host.find(':')==string::npos) - host += ":80"; - RefPtr addr = Net::resolve(host); - delete sock; - sock = new Net::StreamSocket(addr->get_family()); - sock->set_block(false); - - sock->signal_data_available.connect(sigc::mem_fun(this, &Client::data_available)); - sock->signal_connect_finished.connect(sigc::mem_fun(this, &Client::connect_finished)); - if(event_disp) - event_disp->add(*sock); - - sock->connect(*addr); + sock = 0; request = new Request(r); if(!user_agent.empty()) @@ -62,6 +65,17 @@ void Client::start_request(const Request &r) delete response; response = 0; in_buf.clear(); + + string host = r.get_header("Host"); + if(host.find(':')==string::npos) + host += ":80"; + if(resolver) + resolve_tag = resolver->resolve(host); + else + { + RefPtr addr = Net::resolve(host); + address_resolved(resolve_tag, *addr); + } } const Response *Client::get_url(const std::string &url) @@ -104,6 +118,35 @@ void Client::abort() request = 0; } +void Client::address_resolved(unsigned tag, const Net::SockAddr &addr) +{ + if(tag!=resolve_tag) + return; + resolve_tag = 0; + + sock = new Net::StreamSocket(addr.get_family()); + sock->set_block(false); + + sock->signal_data_available.connect(sigc::mem_fun(this, &Client::data_available)); + sock->signal_connect_finished.connect(sigc::mem_fun(this, &Client::connect_finished)); + if(event_disp) + event_disp->add(*sock); + + sock->connect(addr); +} + +void Client::resolve_failed(unsigned tag, const exception &err) +{ + if(tag!=resolve_tag) + return; + resolve_tag = 0; + + signal_socket_error.emit(err); + + delete request; + request = 0; +} + void Client::connect_finished(const exception *err) { if(err) @@ -159,5 +202,23 @@ void Client::data_available() } } + +Client::ResolveListener::ResolveListener(Client &c): + client(c) +{ + client.resolver->signal_address_resolved.connect(sigc::mem_fun(this, &ResolveListener::address_resolved)); + client.resolver->signal_resolve_failed.connect(sigc::mem_fun(this, &ResolveListener::resolve_failed)); +} + +void Client::ResolveListener::address_resolved(unsigned tag, const Net::SockAddr &addr) +{ + client.address_resolved(tag, addr); +} + +void Client::ResolveListener::resolve_failed(unsigned tag, const exception &err) +{ + client.resolve_failed(tag, err); +} + } // namespace Http } // namespace Msp