diff options
| author | Tatsuhiro Tsujikawa <tatsuhiro.t@gmail.com> | 2008-05-05 08:25:41 +0000 |
|---|---|---|
| committer | Tatsuhiro Tsujikawa <tatsuhiro.t@gmail.com> | 2008-05-05 08:25:41 +0000 |
| commit | f596de9eec5ea01a28b7ee5d632164d8b41221ec (patch) | |
| tree | 103c6866eea996f9ab9b31cf3b804eaeb9cf849b /src | |
| parent | b892b54e4b5847ca848a4fda555d4f79d86404e2 (diff) | |
2008-05-05 Tatsuhiro Tsujikawa <tujikawa at rednoah dot com>
Reimplemented transparent metalink using Accept request header.
* src/HttpRequest.cc
* src/HttpRequest.h
* src/HttpRequestCommand.cc
* src/Metalink2RequestGroup.cc
* src/RequestGroup.cc
* src/RequestGroup.h
* test/HttpRequestTest.cc
Diffstat (limited to 'src')
| -rw-r--r-- | src/HttpRequest.cc | 16 | ||||
| -rw-r--r-- | src/HttpRequest.h | 10 | ||||
| -rw-r--r-- | src/HttpRequestCommand.cc | 11 | ||||
| -rw-r--r-- | src/Metalink2RequestGroup.cc | 8 | ||||
| -rw-r--r-- | src/RequestGroup.cc | 26 | ||||
| -rw-r--r-- | src/RequestGroup.h | 10 |
6 files changed, 66 insertions, 15 deletions
diff --git a/src/HttpRequest.cc b/src/HttpRequest.cc index 70e281da..ab260a46 100644 --- a/src/HttpRequest.cc +++ b/src/HttpRequest.cc @@ -44,6 +44,7 @@ #include "prefs.h" #include "AuthConfigFactory.h" #include "AuthConfig.h" +#include "a2functional.h" #include <numeric> namespace aria2 { @@ -145,11 +146,17 @@ std::string HttpRequest::createRequest() const } requestLine += std::string(" HTTP/1.1\r\n")+ - "User-Agent: "+userAgent+"\r\n"+ - "Accept: */*\r\n"+ /* */ + "User-Agent: "+userAgent+"\r\n"; + + requestLine += + std::accumulate(_acceptTypes.begin(), _acceptTypes.end(), + std::string("Accept: */*"), Concat(","))+"\r\n"; /* */ + + requestLine += "Host: "+getHostText(getHost(), getPort())+"\r\n"+ "Pragma: no-cache\r\n"+ "Cache-Control: no-cache\r\n"; + if(!request->isKeepAliveEnabled() && !request->isPipeliningEnabled()) { requestLine += "Connection: close\r\n"; } @@ -232,6 +239,11 @@ void HttpRequest::addHeader(const std::string& headersString) _headers.insert(_headers.end(), headers.begin(), headers.end()); } +void HttpRequest::addAcceptType(const std::string& type) +{ + _acceptTypes.push_back(type); +} + void HttpRequest::configure(const Option* option) { authEnabled = option->get(PREF_HTTP_AUTH_ENABLED) == V_TRUE; diff --git a/src/HttpRequest.h b/src/HttpRequest.h index ddf0ecfe..58798c1d 100644 --- a/src/HttpRequest.h +++ b/src/HttpRequest.h @@ -68,6 +68,8 @@ private: std::deque<std::string> _headers; + std::deque<std::string> _acceptTypes; + std::string getHostText(const std::string& host, uint16_t port) const; std::string getProxyAuthString() const; @@ -171,6 +173,14 @@ public: // accepts multiline headers, deliminated by LF void addHeader(const std::string& headers); + + void addAcceptType(const std::string& type); + + template<typename InputIterator> + void addAcceptType(InputIterator first, InputIterator last) + { + _acceptTypes.insert(_acceptTypes.end(), first, last); + } }; typedef SharedHandle<HttpRequest> HttpRequestHandle; diff --git a/src/HttpRequestCommand.cc b/src/HttpRequestCommand.cc index e552007c..803f876c 100644 --- a/src/HttpRequestCommand.cc +++ b/src/HttpRequestCommand.cc @@ -71,7 +71,7 @@ createHttpRequest(const SharedHandle<Request>& req, const SharedHandle<Segment>& segment, uint64_t totalLength, const Option* option, - const std::deque<std::string>& acceptFeatures) + const RequestGroup* rg) { HttpRequestHandle httpRequest(new HttpRequest()); httpRequest->setUserAgent(option->get(PREF_USER_AGENT)); @@ -79,7 +79,8 @@ createHttpRequest(const SharedHandle<Request>& req, httpRequest->setSegment(segment); httpRequest->setEntityLength(totalLength); httpRequest->addHeader(option->get(PREF_HEADER)); - if(acceptFeatures.size()) { + if(rg->getAcceptFeatures().size()) { + const std::deque<std::string>& acceptFeatures = rg->getAcceptFeatures(); std::string acceptFeaturesHeader = "Accept-Features: "+ Util::trim (std::accumulate(acceptFeatures.begin()+1, acceptFeatures.end(), @@ -88,6 +89,8 @@ createHttpRequest(const SharedHandle<Request>& req, ","); httpRequest->addHeader(acceptFeaturesHeader); } + httpRequest->addAcceptType(rg->getAcceptTypes().begin(), + rg->getAcceptTypes().end()); httpRequest->configure(option); return httpRequest; @@ -103,7 +106,7 @@ bool HttpRequestCommand::executeInternal() { HttpRequestHandle httpRequest (createHttpRequest(req, SharedHandle<Segment>(), _requestGroup->getTotalLength(), e->option, - _requestGroup->getAcceptFeatures())); + _requestGroup)); _httpConnection->sendRequest(httpRequest); } else { for(Segments::iterator itr = _segments.begin(); itr != _segments.end(); ++itr) { @@ -112,7 +115,7 @@ bool HttpRequestCommand::executeInternal() { HttpRequestHandle httpRequest (createHttpRequest(req, segment, _requestGroup->getTotalLength(), e->option, - _requestGroup->getAcceptFeatures())); + _requestGroup)); _httpConnection->sendRequest(httpRequest); } } diff --git a/src/Metalink2RequestGroup.cc b/src/Metalink2RequestGroup.cc index 46dcc2bc..e62c8c7f 100644 --- a/src/Metalink2RequestGroup.cc +++ b/src/Metalink2RequestGroup.cc @@ -169,9 +169,9 @@ Metalink2RequestGroup::createRequestGroup(std::deque<SharedHandle<MetalinkEntry> torrentRg->setDownloadContext(dctx); torrentRg->clearPreDowloadHandler(); torrentRg->clearPostDowloadHandler(); - // remove "metalink" from Accept-Feature list to avoid loop in tranparent + // remove "metalink" from Accept Type list to avoid loop in tranparent // metalink - torrentRg->removeAcceptFeatureHeader(RequestGroup::FEATURE_METALINK); + torrentRg->removeAcceptType(RequestGroup::ACCEPT_METALINK); // make it in-memory download SharedHandle<PreDownloadHandler> preh(new MemoryBufferPreDownloadHandler()); { @@ -222,9 +222,9 @@ Metalink2RequestGroup::createRequestGroup(std::deque<SharedHandle<MetalinkEntry> std::min(_option->getAsInt(PREF_METALINK_SERVERS), entry->maxConnections)); // In metalink, multi connection to a single host is not allowed by default. rg->setSingleHostMultiConnectionEnabled(!_option->getAsBool(PREF_METALINK_ENABLE_UNIQUE_PROTOCOL)); - // remove "metalink" from Accept-Feature list to avoid loop in tranparent + // remove "metalink" from Accept Type list to avoid loop in tranparent // metalink - rg->removeAcceptFeatureHeader(RequestGroup::FEATURE_METALINK); + rg->removeAcceptType(RequestGroup::ACCEPT_METALINK); #ifdef ENABLE_BITTORRENT // Inject depenency between rg and torrentRg here if torrentRg.isNull() == false diff --git a/src/RequestGroup.cc b/src/RequestGroup.cc index 5866cdf4..82e8bc52 100644 --- a/src/RequestGroup.cc +++ b/src/RequestGroup.cc @@ -104,7 +104,7 @@ namespace aria2 { int32_t RequestGroup::_gidCounter = 0; -const std::string RequestGroup::FEATURE_METALINK = "metalink"; +const std::string RequestGroup::ACCEPT_METALINK = "application/metalink+xml"; RequestGroup::RequestGroup(const Option* option, const std::deque<std::string>& uris): @@ -127,11 +127,11 @@ RequestGroup::RequestGroup(const Option* option, } else { _fileAllocationEnabled = false; } - // For now, only supported 'Accept-Features' is "metalink" used for - // transparent metalink. + // Add types to be sent as a Accept header value here. // It would be good to put this value in Option so that user can tweak // and add this list. - _acceptFeatures.push_back(FEATURE_METALINK); + // ACCEPT_METALINK is used for `transparent metalink'. + addAcceptType(ACCEPT_METALINK); initializePreDownloadHandler(); initializePostDownloadHandler(); @@ -969,4 +969,22 @@ void RequestGroup::removeAcceptFeatureHeader(const std::string& feature) } } +const std::deque<std::string>& RequestGroup::getAcceptTypes() const +{ + return _acceptTypes; +} + +void RequestGroup::addAcceptType(const std::string& type) +{ + if(std::find(_acceptTypes.begin(), _acceptTypes.end(), type) == _acceptTypes.end()) { + _acceptTypes.push_back(type); + } +} + +void RequestGroup::removeAcceptType(const std::string& type) +{ + _acceptTypes.erase(std::remove(_acceptTypes.begin(), _acceptTypes.end(), type), + _acceptTypes.end()); +} + } // namespace aria2 diff --git a/src/RequestGroup.h b/src/RequestGroup.h index 657eb2c9..6801c243 100644 --- a/src/RequestGroup.h +++ b/src/RequestGroup.h @@ -110,6 +110,8 @@ private: std::deque<std::string> _acceptFeatures; + std::deque<std::string> _acceptTypes; + const Option* _option; Logger* _logger; @@ -343,7 +345,13 @@ public: void removeAcceptFeatureHeader(const std::string& feature); - static const std::string FEATURE_METALINK; + const std::deque<std::string>& getAcceptTypes() const; + + void addAcceptType(const std::string& type); + + void removeAcceptType(const std::string& type); + + static const std::string ACCEPT_METALINK; }; typedef SharedHandle<RequestGroup> RequestGroupHandle; |
