Ref T42, setup reader

* cache can be prefilled
* renamed to ps_readDistributionInfo
* network issues -> chance to retry
This commit is contained in:
Klaus Basan
2017-04-28 02:37:27 +02:00
committed by Mathew Sutcliffe
parent d46257f670
commit 212bb6b485
2 changed files with 54 additions and 20 deletions

View File

@@ -12,6 +12,7 @@
#include "blackmisc/verify.h" #include "blackmisc/verify.h"
#include "blackmisc/compare.h" #include "blackmisc/compare.h"
#include "blackmisc/fileutils.h" #include "blackmisc/fileutils.h"
#include "blackmisc/directoryutils.h"
#include "blackmisc/json.h" #include "blackmisc/json.h"
#include "blackmisc/logcategory.h" #include "blackmisc/logcategory.h"
#include "blackmisc/logcategorylist.h" #include "blackmisc/logcategorylist.h"
@@ -19,6 +20,7 @@
#include "blackmisc/network/networkutils.h" #include "blackmisc/network/networkutils.h"
#include "blackmisc/network/url.h" #include "blackmisc/network/url.h"
#include "blackmisc/statusmessage.h" #include "blackmisc/statusmessage.h"
#include "blackconfig/buildconfig.h"
#include <QByteArray> #include <QByteArray>
#include <QFile> #include <QFile>
@@ -29,6 +31,7 @@
#include <QUrl> #include <QUrl>
#include <QtGlobal> #include <QtGlobal>
using namespace BlackConfig;
using namespace BlackMisc; using namespace BlackMisc;
using namespace BlackMisc::Db; using namespace BlackMisc::Db;
using namespace BlackMisc::Network; using namespace BlackMisc::Network;
@@ -77,7 +80,7 @@ namespace BlackCore
const bool cacheAvailable = cachedSetup.wasLoaded(); const bool cacheAvailable = cachedSetup.wasLoaded();
msgs.push_back(cacheAvailable ? msgs.push_back(cacheAvailable ?
CStatusMessage(this, CStatusMessage::SeverityInfo , "Cached setup synchronized and contains data") : CStatusMessage(this, CStatusMessage::SeverityInfo , "Cached setup synchronized and contains data") :
CStatusMessage(this, CStatusMessage::SeverityInfo , "Cached setup synchronized, but no data") CStatusMessage(this, CStatusMessage::SeverityInfo , "Cached setup synchronized, but no data in cache")
); );
if (this->m_bootstrapMode == CacheOnly) if (this->m_bootstrapMode == CacheOnly)
{ {
@@ -114,13 +117,14 @@ namespace BlackCore
} }
else else
{ {
msgs.push_back(CStatusMessage(this, CStatusMessage::SeverityInfo, "Empty cache, will not add URLs")); msgs.push_back(CStatusMessage(this, CStatusMessage::SeverityInfo, "Empty cache, will not add URLs from cache"));
} }
this->m_bootstrapUrls.removeDuplicates(); // clean up this->m_bootstrapUrls.removeDuplicates(); // clean up
if (this->m_bootstrapUrls.isEmpty()) if (this->m_bootstrapUrls.isEmpty())
{ {
// after all still empty // after all still empty
msgs.push_back(CStatusMessage(this, CStatusMessage::SeverityInfo, "Your log files are here: " + CDirectoryUtils::getLogDirectory()));
msgs.push_back(CStatusMessage(this, CStatusMessage::SeverityError, "No bootstrap URLs, cannot load setup")); msgs.push_back(CStatusMessage(this, CStatusMessage::SeverityError, "No bootstrap URLs, cannot load setup"));
} }
else else
@@ -171,11 +175,19 @@ namespace BlackCore
{ {
if (!url.isLocalFile()) if (!url.isLocalFile())
{ {
if (!CNetworkUtils::canConnect(url)) bool retry = false;
bool ok = false;
do
{ {
sApp->cmdLineErrorMessage(QString("URL '%1' not reachable").arg(urlString)); if (CNetworkUtils::canConnect(url, CNetworkUtils::getLongTimeoutMs()))
return false; {
ok = true;
break;
}
retry = sApp->cmdLineErrorMessage(QString("URL '%1' not reachable").arg(urlString), true);
} }
while (retry);
if (!ok) { return false; }
} }
} }
return true; return true;
@@ -200,7 +212,7 @@ namespace BlackCore
if (this->m_shutdown) { return CStatusMessage(this, CStatusMessage::SeverityError, "shutdown"); } if (this->m_shutdown) { return CStatusMessage(this, CStatusMessage::SeverityError, "shutdown"); }
if (!sApp->isNetworkAccessible()) if (!sApp->isNetworkAccessible())
{ {
const CStatusMessage m(this, CStatusMessage::SeverityError, "No network, cancelled reading of setup"); const CStatusMessage m(this, CStatusMessage::SeverityInfo, "No network, will try to recover");
CStatusMessageList msgs(m); CStatusMessageList msgs(m);
msgs.push_back(this->manageSetupAvailability(false, false)); msgs.push_back(this->manageSetupAvailability(false, false));
this->setLastSetupReadErrorMessages(msgs); this->setLastSetupReadErrorMessages(msgs);
@@ -214,6 +226,7 @@ namespace BlackCore
"Cannot read setup, URLs: " + this->m_bootstrapUrls.toQString() + "Cannot read setup, URLs: " + this->m_bootstrapUrls.toQString() +
" failed URLs: " + this->m_bootstrapUrls.getFailedUrls().toQString()); " failed URLs: " + this->m_bootstrapUrls.getFailedUrls().toQString());
CStatusMessageList msgs(m); CStatusMessageList msgs(m);
msgs.push_back(CNetworkUtils::createNetworkReport(sApp->getNetworkAccessManager()));
msgs.push_back(this->manageSetupAvailability(false, false)); msgs.push_back(this->manageSetupAvailability(false, false));
this->setLastSetupReadErrorMessages(msgs); this->setLastSetupReadErrorMessages(msgs);
return msgs; return msgs;
@@ -224,14 +237,13 @@ namespace BlackCore
return m; return m;
} }
void CSetupReader::ps_readUpdateInfo() void CSetupReader::ps_readDistributionInfo()
{ {
const CUrl url(this->m_distributionUrls.obtainNextWorkingUrl()); const CUrl url(this->m_distributionUrls.obtainNextWorkingUrl());
if (url.isEmpty()) if (url.isEmpty())
{ {
CLogMessage(this).warning("Cannot read update info, URLs: '%1', failed URLs: '%2'") CLogMessage(this).warning("Cannot read update info, URLs: '%1', failed URLs: '%2'") << this->m_distributionUrls << this->m_distributionUrls.getFailedUrls();
<< this->m_distributionUrls CLogMessage::preformatted(CNetworkUtils::createNetworkReport(sApp->getNetworkAccessManager()));
<< this->m_distributionUrls.getFailedUrls();
this->manageDistributionsInfoAvailability(false); this->manageDistributionsInfoAvailability(false);
return; return;
} }
@@ -258,7 +270,7 @@ namespace BlackCore
return url; return url;
} }
CStatusMessageList CSetupReader::readLocalBootstrapFile(QString &fileName) CStatusMessageList CSetupReader::readLocalBootstrapFile(const QString &fileName)
{ {
if (fileName.isEmpty()) { return CStatusMessage(this).error("No file name for local bootstrap file"); } if (fileName.isEmpty()) { return CStatusMessage(this).error("No file name for local bootstrap file"); }
QString fn; QString fn;
@@ -465,7 +477,7 @@ namespace BlackCore
// try next one if any // try next one if any
if (this->m_distributionUrls.addFailedUrl(url)) if (this->m_distributionUrls.addFailedUrl(url))
{ {
QTimer::singleShot(500, this, &CSetupReader::ps_readUpdateInfo); QTimer::singleShot(500, this, &CSetupReader::ps_readDistributionInfo);
} }
else else
{ {
@@ -495,6 +507,23 @@ namespace BlackCore
return m_setup.get(); return m_setup.get();
} }
bool CSetupReader::prefillCacheWithLocalResourceBootstrapFile()
{
if (m_shutdown) { return false; }
this->m_setup.synchronize(); // make sure it is loaded
const CGlobalSetup cachedSetup = m_setup.get();
const bool cacheAvailable = cachedSetup.wasLoaded();
if (cacheAvailable)
{
CLogMessage(this).info("Setup (bootstrap already cached, no prefill needed");
return false;
}
const QString fn = CBuildConfig::getBootstrapResourceFile();
const CStatusMessageList msgs = this->readLocalBootstrapFile(fn);
CLogMessage::preformatted(msgs);
return true;
}
QString CSetupReader::getLastSuccessfulSetupUrl() const QString CSetupReader::getLastSuccessfulSetupUrl() const
{ {
QReadLocker l(&m_lockSetup); QReadLocker l(&m_lockSetup);
@@ -530,13 +559,13 @@ namespace BlackCore
CStatusMessageList msgs; CStatusMessageList msgs;
if (webRead) if (webRead)
{ {
msgs.push_back(CStatusMessage(this).info("Setup loaded from web, will trigger read of update information")); msgs.push_back(CStatusMessage(this).info("Setup loaded from web, will trigger read of distribution information"));
QTimer::singleShot(500, this, &CSetupReader::ps_readUpdateInfo); QTimer::singleShot(500, this, &CSetupReader::ps_readDistributionInfo);
} }
if (localRead) if (localRead)
{ {
msgs.push_back(CStatusMessage(this).info("Setup loaded locally, will trigger read of update information")); msgs.push_back(CStatusMessage(this).info("Setup loaded locally, will trigger read of distribution information"));
QTimer::singleShot(500, this, &CSetupReader::ps_readUpdateInfo); QTimer::singleShot(500, this, &CSetupReader::ps_readDistributionInfo);
} }
bool available = false; bool available = false;

View File

@@ -64,6 +64,11 @@ namespace BlackCore
//! \threadsafe //! \threadsafe
BlackCore::Data::CGlobalSetup getSetup() const; BlackCore::Data::CGlobalSetup getSetup() const;
//! Load the cache file local boostrap file
//! \remark can be used during installation as failover
//! \threadsafe
bool prefillCacheWithLocalResourceBootstrapFile();
//! Last distribution URL successfully read //! Last distribution URL successfully read
//! \threadsafe //! \threadsafe
QString getLastSuccessfulSetupUrl() const; QString getLastSuccessfulSetupUrl() const;
@@ -120,8 +125,8 @@ namespace BlackCore
//! Do reading //! Do reading
void ps_readSetup(); void ps_readSetup();
//! Do reading //! Do reading of distributions
void ps_readUpdateInfo(); void ps_readDistributionInfo();
//! Setup has been changed //! Setup has been changed
void ps_setupChanged(); void ps_setupChanged();
@@ -135,7 +140,7 @@ namespace BlackCore
CacheOnly CacheOnly
}; };
bool m_shutdown = false; std::atomic<bool> m_shutdown { false };
std::atomic<bool> m_setupAvailable { false }; std::atomic<bool> m_setupAvailable { false };
std::atomic<bool> m_distributionInfoAvailable { false }; std::atomic<bool> m_distributionInfoAvailable { false };
QString m_localSetupFileValue; //! Local file for setup, passed by cmd line arguments QString m_localSetupFileValue; //! Local file for setup, passed by cmd line arguments
@@ -154,7 +159,7 @@ namespace BlackCore
BlackMisc::CData<BlackMisc::Db::TDistributionInfo> m_distributions {this}; //!< data cache distributions BlackMisc::CData<BlackMisc::Db::TDistributionInfo> m_distributions {this}; //!< data cache distributions
//! Read by local individual file and update cache from that //! Read by local individual file and update cache from that
BlackMisc::CStatusMessageList readLocalBootstrapFile(QString &fileName); BlackMisc::CStatusMessageList readLocalBootstrapFile(const QString &fileName);
//! Trigger reading //! Trigger reading
BlackMisc::CStatusMessageList triggerReadSetup(); BlackMisc::CStatusMessageList triggerReadSetup();