Be more resilient to potential aria2 error.

This commit is contained in:
Matthieu Gautier 2018-10-16 17:42:16 +02:00
parent bb1f777078
commit 8176a6eded
2 changed files with 23 additions and 10 deletions

View File

@ -35,6 +35,11 @@ struct DownloadedFile {
std::string path; std::string path;
}; };
class AriaError : public std::runtime_error {
public:
AriaError(const std::string& message) : std::runtime_error(message) {}
};
/** /**
* A tool to download things. * A tool to download things.
* *

View File

@ -7,6 +7,7 @@
#include <chrono> #include <chrono>
#include <common/otherTools.h> #include <common/otherTools.h>
#include <common/pathTools.h> #include <common/pathTools.h>
#include <downloader.h> // For AriaError
namespace kiwix { namespace kiwix {
@ -56,19 +57,25 @@ Aria2::Aria2():
callCmd.push_back("--max-concurrent-downloads=42"); callCmd.push_back("--max-concurrent-downloads=42");
callCmd.push_back("--rpc-max-request-size=6M"); callCmd.push_back("--rpc-max-request-size=6M");
callCmd.push_back("--file-allocation=none"); callCmd.push_back("--file-allocation=none");
callCmd.push_back(NULL);
mp_aria = Subprocess::run(callCmd); mp_aria = Subprocess::run(callCmd);
mp_curl = curl_easy_init(); mp_curl = curl_easy_init();
curl_easy_setopt(mp_curl, CURLOPT_URL, "http://localhost/rpc"); curl_easy_setopt(mp_curl, CURLOPT_URL, "http://localhost/rpc");
curl_easy_setopt(mp_curl, CURLOPT_PORT, m_port); curl_easy_setopt(mp_curl, CURLOPT_PORT, m_port);
curl_easy_setopt(mp_curl, CURLOPT_POST, 1L); curl_easy_setopt(mp_curl, CURLOPT_POST, 1L);
while(true) { int watchdog = 50;
while(--watchdog) {
std::this_thread::sleep_for(std::chrono::microseconds(100)); std::this_thread::sleep_for(std::chrono::microseconds(100));
auto res = curl_easy_perform(mp_curl); auto res = curl_easy_perform(mp_curl);
if (res == CURLE_OK) { if (res == CURLE_OK) {
break; break;
} }
} }
if (!watchdog) {
curl_easy_cleanup(mp_curl);
throw std::runtime_error("Cannot connect to aria2c rpc");
}
} }
Aria2::~Aria2() Aria2::~Aria2()
@ -104,12 +111,18 @@ std::string Aria2::doRequest(const MethodCall& methodCall)
long response_code; long response_code;
curl_easy_getinfo(mp_curl, CURLINFO_RESPONSE_CODE, &response_code); curl_easy_getinfo(mp_curl, CURLINFO_RESPONSE_CODE, &response_code);
pthread_mutex_unlock(&m_lock); pthread_mutex_unlock(&m_lock);
if (response_code == 200) { if (response_code != 200) {
return stringstream.str(); throw std::runtime_error("Invalid return code from aria");
} }
auto responseContent = stringstream.str();
MethodResponse response(responseContent);
if (response.isFault()) {
throw AriaError(response.getFault().getFaultString());
}
return responseContent;
} }
pthread_mutex_unlock(&m_lock); pthread_mutex_unlock(&m_lock);
return ""; throw std::runtime_error("Cannot perform request");
} }
std::string Aria2::addUri(const std::vector<std::string>& uris) std::string Aria2::addUri(const std::vector<std::string>& uris)
@ -121,12 +134,7 @@ std::string Aria2::addUri(const std::vector<std::string>& uris)
} }
auto ret = doRequest(methodCall); auto ret = doRequest(methodCall);
MethodResponse response(ret); MethodResponse response(ret);
try { return response.getParamValue(0).getAsS();
return response.getParams().getParam(0).getValue().getAsS();
} catch (InvalidRPCNode& err) {
std::cerr << response.getFault().getFaultString();
}
return "";
} }
std::string Aria2::tellStatus(const std::string& gid, const std::vector<std::string>& statusKey) std::string Aria2::tellStatus(const std::string& gid, const std::vector<std::string>& statusKey)