diff --git a/include/config.h b/include/config.h index 09a4e1e..5c090ca 100644 --- a/include/config.h +++ b/include/config.h @@ -65,10 +65,11 @@ class Config std::string sLanguagePackSubdir; std::string sDLCSubdir; std::string sGameSubdir; - std::string sLanguagePriority; - std::string sPlatformPriority; - std::vector vLanguagePriority; - std::vector vPlatformPriority; + std::string sFileIdString; + std::string sLanguagePriority; + std::string sPlatformPriority; + std::vector vLanguagePriority; + std::vector vPlatformPriority; unsigned int iInstallerType; unsigned int iInstallerLanguage; diff --git a/include/downloader.h b/include/downloader.h index 49cab87..d701714 100644 --- a/include/downloader.h +++ b/include/downloader.h @@ -67,6 +67,7 @@ class Downloader void checkOrphans(); void checkStatus(); void updateCache(); + void downloadFileWithId(const std::string& fileid_string); CURL* curlhandle; Timer timer; Config config; diff --git a/main.cpp b/main.cpp index ba908de..1aab8fb 100644 --- a/main.cpp +++ b/main.cpp @@ -150,6 +150,7 @@ int main(int argc, char *argv[]) ("no-cover", bpo::value(&bNoCover)->zero_tokens()->default_value(false), "Don't download cover images. Overrides --cover option.\nUseful for making exceptions when \"cover\" is set to true in config file.") ("update-cache", bpo::value(&config.bUpdateCache)->zero_tokens()->default_value(false), "Update game details cache") ("no-platform-detection", bpo::value(&bNoPlatformDetection)->zero_tokens()->default_value(false), "Don't try to detect supported platforms from game shelf.\nSkips the initial fast platform detection and detects the supported platforms from game details which is slower but more accurate.\nUseful in case platform identifier is missing for some games in the game shelf.\nUsing --platform with --list doesn't work with this option.") + ("download-file", bpo::value(&config.sFileIdString)->default_value(""), "Download a single file using fileid\nFormat: \"gamename/fileid\"\nThis option ignores all subdir options. The file is downloaded to directory specified with --directory option.") ; // Commandline options (config file) options_cli_cfg.add_options() @@ -512,6 +513,8 @@ int main(int argc, char *argv[]) downloader.updateCache(); else if (config.bUpdateCheck) // Update check has priority over download and list downloader.updateCheck(); + else if (!config.sFileIdString.empty()) + downloader.downloadFileWithId(config.sFileIdString); else if (config.bRepair) // Repair file downloader.repair(); else if (config.bDownload) // Download games diff --git a/src/downloader.cpp b/src/downloader.cpp index 14d6c57..dd499bc 100644 --- a/src/downloader.cpp +++ b/src/downloader.cpp @@ -90,7 +90,7 @@ int Downloader::init() // updateCheck() calls getGameList() if needed // getGameList() is not needed when using cache unless we want to list games from account - if ( !config.bUpdateCheck && (!config.bUseCache || (config.bUseCache && config.bList)) ) + if ( !config.bUpdateCheck && (!config.bUseCache || (config.bUseCache && config.bList)) && config.sFileIdString.empty() ) this->getGameList(); if (config.bReport && (config.bDownload || config.bRepair)) @@ -3076,3 +3076,42 @@ void Downloader::saveSerials(const std::string& serials, const std::string& file return; } + +void Downloader::downloadFileWithId(const std::string& fileid_string) +{ + size_t pos = fileid_string.find("/"); + if (pos == std::string::npos) + { + std::cout << "Invalid file id " << fileid_string << ": could not find separator \"/\"" << std::endl; + } + else + { + std::string gamename, fileid, url; + gamename.assign(fileid_string.begin(), fileid_string.begin()+pos); + fileid.assign(fileid_string.begin()+pos+1, fileid_string.end()); + + if (fileid.find("installer") != std::string::npos) + url = gogAPI->getInstallerLink(gamename, fileid); + else if (fileid.find("patch") != std::string::npos) + url = gogAPI->getPatchLink(gamename, fileid); + else + url = gogAPI->getExtraLink(gamename, fileid); + + if (!gogAPI->getError()) + { + std::string filename, filepath; + filename.assign(url.begin()+url.find_last_of("/")+1, url.begin()+url.find_first_of("?")); + filepath = Util::makeFilepath(config.sDirectory, filename, gamename); + std::cout << "Downloading: " << filepath << std::endl; + this->downloadFile(url, filepath, std::string(), gamename); + std::cout << std::endl; + } + else + { + std::cout << gogAPI->getErrorMessage() << std::endl; + gogAPI->clearError(); + } + } + + return; +}