refs #614, moved cache to vPilot reader

This commit is contained in:
Klaus Basan
2016-03-29 09:28:46 +02:00
parent 01d4faa20f
commit a1d6492ff2
4 changed files with 72 additions and 30 deletions

View File

@@ -99,7 +99,7 @@ namespace BlackMisc
//! Trait for vPilot derived models
struct VPilotAircraftModels : public BlackMisc::CDataTrait<BlackMisc::Simulation::CAircraftModelList>
struct VPilotAircraftModels : public ModelCache
{
//! Key in data cache
static const char *key() { return "vpilot/models"; }

View File

@@ -8,7 +8,7 @@
*/
#include "vpilotrulesreader.h"
#include "blackmisc/logmessage.h"
#include <QtXml/QDomElement>
#include <QFile>
#include <QDir>
@@ -73,26 +73,26 @@ namespace BlackMisc
int CVPilotRulesReader::getModelsCount() const
{
QReadLocker l(&m_lockData);
return m_models.size();
return this->m_cachedVPilotModels.get().size();
}
CAircraftModelList CVPilotRulesReader::getAsModels() const
CAircraftModelList CVPilotRulesReader::getAsModels()
{
// already cached?
{
QReadLocker l(&m_lockData);
if (!m_models.isEmpty() || m_rules.isEmpty()) { return m_models; }
if (m_shutdown) { return CAircraftModelList(); }
}
CAircraftModelList vPilotModels(this->m_cachedVPilotModels.getCopy());
if (!vPilotModels.isEmpty() || m_rules.isEmpty()) { return vPilotModels; }
// important: that can take a while and should normally
// run in background
CVPilotModelRuleSet rules(getRules()); // thread safe copy
CAircraftModelList models(rules.toAircraftModels()); // long lasting operation
QWriteLocker l(&m_lockData);
m_models = models;
return m_models;
const CVPilotModelRuleSet rules(getRules()); // thread safe copy
vPilotModels = rules.toAircraftModels(); // long lasting operation
this->ps_setCache(vPilotModels);
return vPilotModels;
}
CAircraftModelList CVPilotRulesReader::getAsModelsFromCache() const
{
return this->m_cachedVPilotModels.getCopy();
}
int CVPilotRulesReader::countRulesLoaded() const
@@ -137,14 +137,17 @@ namespace BlackMisc
}
{
QWriteLocker l(&m_lockData);
this->m_loadedFiles = loadedFiles;
this->m_fileListWithProblems = filesWithProblems;
this->m_rules = rules;
{
QWriteLocker l(&m_lockData);
this->m_loadedFiles = loadedFiles;
this->m_fileListWithProblems = filesWithProblems;
this->m_rules = rules;
if (m_shutdown) { return false; }
}
if (convertToModels)
{
if (m_shutdown) { return false; }
this->m_models = rules.toAircraftModels(); // long lasting operation
const CAircraftModelList vPilotModels(rules.toAircraftModels()); // long lasting operation
this->ps_setCache(vPilotModels);
}
}
@@ -174,6 +177,31 @@ namespace BlackMisc
m_asyncLoadInProgress = false;
}
void CVPilotRulesReader::ps_onVPilotCacheChanged()
{
// void
}
void CVPilotRulesReader::ps_setCache(const CAircraftModelList &models)
{
if (this->m_cachedVPilotModels.isOwnerThread())
{
CStatusMessage m;
{
QWriteLocker l(&m_lockData);
m = this->m_cachedVPilotModels.set(models);
}
if (m.isFailure())
{
CLogMessage::preformatted(m);
}
}
else
{
QTimer::singleShot(0, this, [this, models]() { this->ps_setCache(models); });
}
}
bool CVPilotRulesReader::loadFile(const QString &fileName, CVPilotModelRuleSet &ruleSet)
{
QFile f(fileName);
@@ -189,7 +217,7 @@ namespace BlackMisc
QDomNodeList mmRuleSet = doc.elementsByTagName("ModelMatchRuleSet");
if (mmRuleSet.size() < 1) { return true; }
QDomNamedNodeMap attributes = mmRuleSet.at(0).attributes();
const QDomNamedNodeMap attributes = mmRuleSet.at(0).attributes();
QString folder = attributes.namedItem("Folder").nodeValue().trimmed();
if (folder.isEmpty())
{
@@ -197,18 +225,18 @@ namespace BlackMisc
}
// "2/1/2014 12:00:00 AM", "5/26/2014 2:00:00 PM"
QString updated = attributes.namedItem("UpdatedOn").nodeValue();
const QString updated = attributes.namedItem("UpdatedOn").nodeValue();
QDateTime qt = QDateTime::fromString(updated, "M/d/yyyy h:mm:ss AP");
qint64 updatedTimestamp = qt.toMSecsSinceEpoch();
int rulesSize = rules.size();
for (int i = 0; i < rulesSize; i++)
{
QDomNamedNodeMap attributes = rules.at(i).attributes();
const QString typeCode = attributes.namedItem("TypeCode").nodeValue();
const QString modelName = attributes.namedItem("ModelName").nodeValue();
const QDomNamedNodeMap ruleAttributes = rules.at(i).attributes();
const QString typeCode = ruleAttributes.namedItem("TypeCode").nodeValue();
const QString modelName = ruleAttributes.namedItem("ModelName").nodeValue();
// remark, callsign prefix is airline ICAO code
const QString callsignPrefix = attributes.namedItem("CallsignPrefix").nodeValue();
const QString callsignPrefix = ruleAttributes.namedItem("CallsignPrefix").nodeValue();
if (modelName.isEmpty()) { continue; }
// split if we have multiple models

View File

@@ -16,6 +16,7 @@
#include "blackmisc/worker.h"
#include "blackmisc/simulation/aircraftmodellist.h"
#include "blackmisc/simulation/fscommon/vpilotmodelruleset.h"
#include "blackmisc/simulation/data/modelcaches.h"
#include <QStringList>
#include <QObject>
#include <QReadWriteLock>
@@ -60,7 +61,11 @@ namespace BlackMisc
//! Get as models
//! \threadsafe
BlackMisc::Simulation::CAircraftModelList getAsModels() const;
BlackMisc::Simulation::CAircraftModelList getAsModels();
//! Get as models from cache
//! \threadsafe
BlackMisc::Simulation::CAircraftModelList getAsModelsFromCache() const;
//! Get model count
//! \threadsafe
@@ -95,6 +100,13 @@ namespace BlackMisc
//! \threadsafe
void ps_readInBackgroundFinished();
//! Cache changed
void ps_onVPilotCacheChanged();
//! Set cache (in main thread)
//! \threadsafe
void ps_setCache(const BlackMisc::Simulation::CAircraftModelList &models);
private:
QStringList m_fileList; //!< list of file names
QStringList m_fileListWithProblems; //!< problems during parsing
@@ -102,13 +114,12 @@ namespace BlackMisc
CVPilotModelRuleSet m_rules; //!< rules list
bool m_asyncLoadInProgress = false; //!< Asynchronous load in progress
bool m_shutdown = false; //!< Shutdown
mutable BlackMisc::Simulation::CAircraftModelList m_models; //!< converted to models
BlackMisc::CData<BlackMisc::Simulation::Data::VPilotAircraftModels> m_cachedVPilotModels { this, &CVPilotRulesReader::ps_onVPilotCacheChanged }; //!< cache for latest vPilot rules
mutable QReadWriteLock m_lockData;
//! Read single file and do parsing
//! \threadsafe
bool loadFile(const QString &fileName, CVPilotModelRuleSet &ruleSet);
};
} // namespace
} // namespace

View File

@@ -303,6 +303,9 @@ namespace BlackMisc
//! Write and save in the same step. Must be called from the thread in which the owner lives.
CStatusMessage setAndSave(const T &value, qint64 timestamp = 0) { return m_page.setValue(m_element, CVariant::from(value), timestamp, true); }
//! Is current thread the owner thread, so CCached::set is safe
bool isOwnerThread() const { return QThread::currentThread() == m_page.thread(); }
//! Get the key string of this value.
const QString &getKey() const { return m_page.getKey(m_element); }