X-Git-Url: https://git.mxchange.org/?a=blobdiff_plain;f=simgear%2Fpackage%2FCatalog.cxx;h=c9c6565836ae0a4d970fb8c76671e8477fbef496;hb=a3f1bb546fec72b07f11f69934e6894696fea57a;hp=87e2a3921369391c5dde2d082fe1c7b42bd3a2d3;hpb=3bfd0c872a7807c2a648e4435047fed4a52e555b;p=simgear.git diff --git a/simgear/package/Catalog.cxx b/simgear/package/Catalog.cxx index 87e2a392..c9c65658 100644 --- a/simgear/package/Catalog.cxx +++ b/simgear/package/Catalog.cxx @@ -31,6 +31,7 @@ #include #include #include +#include namespace simgear { @@ -40,18 +41,32 @@ bool checkVersion(const std::string& aVersion, SGPropertyNode_ptr props) { BOOST_FOREACH(SGPropertyNode* v, props->getChildren("version")) { std::string s(v->getStringValue()); - if (s== aVersion) { + if (s == aVersion) { return true; } - // allow 3.5.* to match any of 3.5.0, 3.5.1rc1, 3.5.11 or so on - if (strutils::ends_with(s, ".*")) { - size_t lastDot = aVersion.rfind('.'); - std::string ver = aVersion.substr(0, lastDot); - if (ver == s.substr(0, s.length() - 2)) { - return true; + // examine each dot-seperated component in turn, supporting a wildcard + // in the versions from the catalog. + string_list appVersionParts = simgear::strutils::split(aVersion, "."); + string_list catVersionParts = simgear::strutils::split(s, "."); + + size_t partCount = appVersionParts.size(); + if (partCount != catVersionParts.size()) { + continue; + } + + bool ok = true; + for (unsigned int p=0; p < partCount; ++p) { + if (catVersionParts[p] == "*") { + // always passes + } else if (appVersionParts[p] != catVersionParts[p]) { + ok = false; } } + + if (ok) { + return true; + } } return false; } @@ -63,7 +78,7 @@ std::string redirectUrlForVersion(const std::string& aVersion, SGPropertyNode_pt return v->getStringValue("url"); } } - + return std::string(); } @@ -196,22 +211,13 @@ CatalogRef Catalog::createFromPath(Root* aRoot, const SGPath& aPath) return NULL; } - if (!checkVersion(aRoot->applicationVersion(), props)) { - std::string redirect = redirectUrlForVersion(aRoot->applicationVersion(), props); - if (!redirect.empty()) { - SG_LOG(SG_GENERAL, SG_WARN, "catalog at " << aPath << ", version mismatch:\n\t" - << "redirecting to alternate URL:" << redirect); - CatalogRef c = Catalog::createFromUrl(aRoot, redirect); - c->m_installRoot = aPath; - return c; - } else { - SG_LOG(SG_GENERAL, SG_WARN, "skipping catalog at " << aPath << ", version mismatch:\n\t" - << props->getStringValue("version") << " vs required " << aRoot->catalogVersion()); - return NULL; - } + bool versionCheckOk = checkVersion(aRoot->applicationVersion(), props); + if (!versionCheckOk) { + SG_LOG(SG_GENERAL, SG_INFO, "catalog at:" << aPath << " failed version check: need" << aRoot->applicationVersion()); + // keep the catalog but mark it as needing an update } else { - SG_LOG(SG_GENERAL, SG_INFO, "creating catalog from:" << aPath); + SG_LOG(SG_GENERAL, SG_DEBUG, "creating catalog from:" << aPath); } CatalogRef c = new Catalog(aRoot); @@ -219,8 +225,12 @@ CatalogRef Catalog::createFromPath(Root* aRoot, const SGPath& aPath) c->parseProps(props); c->parseTimestamp(); - // parsed XML ok, mark status as valid - c->changeStatus(Delegate::STATUS_SUCCESS); + if (versionCheckOk) { + // parsed XML ok, mark status as valid + c->changeStatus(Delegate::STATUS_SUCCESS); + } else { + c->changeStatus(Delegate::FAIL_VERSION); + } return c; } @@ -229,7 +239,7 @@ bool Catalog::uninstall() { bool ok; bool atLeastOneFailure = false; - + BOOST_FOREACH(PackageRef p, installedPackages()) { ok = p->existingInstall()->uninstall(); if (!ok) { @@ -246,7 +256,7 @@ bool Catalog::uninstall() if (!ok) { atLeastOneFailure = true; } - + changeStatus(atLeastOneFailure ? Delegate::FAIL_FILESYSTEM : Delegate::STATUS_SUCCESS); return ok; @@ -314,15 +324,15 @@ void Catalog::refresh() struct FindById { FindById(const std::string &id) : m_id(id) {} - + bool operator()(const PackageRef& ref) const { return ref->id() == m_id; } - + std::string m_id; }; - + void Catalog::parseProps(const SGPropertyNode* aProps) { // copy everything except package children? @@ -338,7 +348,7 @@ void Catalog::parseProps(const SGPropertyNode* aProps) if (strcmp(pkgProps->getName(), "package") == 0) { // can't use getPackageById here becuase the variant dict isn't // built yet. Instead we need to look at m_packages directly. - + PackageList::iterator pit = std::find_if(m_packages.begin(), m_packages.end(), FindById(pkgProps->getStringValue("id"))); PackageRef p; @@ -428,6 +438,11 @@ std::string Catalog::url() const return m_url; } +std::string Catalog::name() const +{ + return getLocalisedString(m_props, "name"); +} + std::string Catalog::description() const { return getLocalisedString(m_props, "description"); @@ -464,6 +479,11 @@ unsigned int Catalog::ageInSeconds() const bool Catalog::needsRefresh() const { + // always refresh in these cases + if ((m_status == Delegate::FAIL_VERSION) || (m_status == Delegate::FAIL_DOWNLOAD)) { + return true; + } + unsigned int maxAge = m_props->getIntValue("max-age-sec", m_root->maxAgeSeconds()); return (ageInSeconds() > maxAge); } @@ -473,7 +493,7 @@ std::string Catalog::getLocalisedString(const SGPropertyNode* aRoot, const char* if (!aRoot) { return std::string(); } - + if (aRoot->hasChild(m_root->getLocale())) { const SGPropertyNode* localeRoot = aRoot->getChild(m_root->getLocale().c_str()); if (localeRoot->hasChild(aName)) { @@ -495,7 +515,7 @@ void Catalog::changeStatus(Delegate::StatusCode newStatus) if (m_status == newStatus) { return; } - + m_status = newStatus; m_root->catalogRefreshStatus(this, newStatus); m_statusCallbacks(this);