- dont overwrite an invalid settings file in any case

- fix file writing
This commit is contained in:
Dorian Zedler 2021-07-17 16:49:15 +02:00
parent 9dad927239
commit 5f429f4558
Signed by: dorian
GPG key ID: 989DE36109AFA354
2 changed files with 27 additions and 6 deletions

View file

@ -34,7 +34,7 @@ class ScStwSettings : public QObject
{ {
Q_OBJECT Q_OBJECT
public: public:
explicit ScStwSettings(QObject *parent = nullptr); explicit ScStwSettings(QObject *parent = nullptr, bool overwriteFileOnErrors = true);
typedef QString(*keyToStringConverter)(int); typedef QString(*keyToStringConverter)(int);
typedef QVariant::Type(*keyToTypeConverter)(int); typedef QVariant::Type(*keyToTypeConverter)(int);
@ -104,6 +104,8 @@ protected:
bool registerKeyLevelConverters(int keyLevel, keyToStringConverter, keyToTypeConverter); bool registerKeyLevelConverters(int keyLevel, keyToStringConverter, keyToTypeConverter);
private: private:
bool fileIsReadonly;
QFile * settingsFile; QFile * settingsFile;
QVariantMap settingsCache; QVariantMap settingsCache;

View file

@ -18,7 +18,7 @@
#include "../headers/scstwsettings.h" #include "../headers/scstwsettings.h"
ScStwSettings::ScStwSettings(QObject *parent) : QObject(parent) ScStwSettings::ScStwSettings(QObject *parent, bool overwriteFileOnErrors) : QObject(parent)
{ {
#ifdef RASPI #ifdef RASPI
QString path = "/root/.config/ScStwBasestation"; QString path = "/root/.config/ScStwBasestation";
@ -30,13 +30,20 @@ ScStwSettings::ScStwSettings(QObject *parent) : QObject(parent)
qFatal("[FATAL] Failed to create writable directory for settings at %s", qPrintable(path)); qFatal("[FATAL] Failed to create writable directory for settings at %s", qPrintable(path));
this->settingsFile = new QFile(path + "/settings.json"); this->settingsFile = new QFile(path + "/settings.json");
this->fileIsReadonly = false;
if(!this->settingsFile->open(QFile::ReadWrite)) if(!this->settingsFile->open(QFile::ReadWrite))
qFatal("[FATAL] Couldn't open settings file %s", qPrintable(path + "/settings.json")); qFatal("[FATAL] Couldn't open settings file %s", qPrintable(path + "/settings.json"));
if(!this->loadSettingsFromFile() && this->settingsFile->size() != 0) { if(this->settingsFile->size() != 0 && !this->loadSettingsFromFile()) {
this->writeSettingsToFile(); if(overwriteFileOnErrors) {
qWarning("[WARNING] Settings file (%s) was of invalid format and therefore overwritten!", qPrintable(path + "/settings.json")); this->writeSettingsToFile();
qWarning("[WARNING] Settings file (%s) was of invalid format and therefore overwritten!", qPrintable(path + "/settings.json"));
}
else {
qWarning("[WARNING] Settings file (%s) was of invalid format!", qPrintable(path + "/settings.json"));
this->fileIsReadonly = true;
}
} }
connect(this, &ScStwSettings::settingChanged, this, &ScStwSettings::writeSettingsToFile); connect(this, &ScStwSettings::settingChanged, this, &ScStwSettings::writeSettingsToFile);
@ -144,9 +151,15 @@ bool ScStwSettings::registerKeyLevelConverters(int keyLevel, keyToStringConverte
*/ */
bool ScStwSettings::writeSettingsToFile() { bool ScStwSettings::writeSettingsToFile() {
if(this->fileIsReadonly) {
qWarning() << "[WARNING][SETTINS] Cannot write changes to file! It has been marked readonly due to parse errors (see above).";
return false;
}
QJsonDocument doc = QJsonDocument::fromVariant(this->settingsCache); QJsonDocument doc = QJsonDocument::fromVariant(this->settingsCache);
// overwrite file // overwrite file
this->settingsFile->resize(0);
this->settingsFile->reset(); this->settingsFile->reset();
this->settingsFile->write(doc.toJson(QJsonDocument::Indented)); this->settingsFile->write(doc.toJson(QJsonDocument::Indented));
this->settingsFile->flush(); this->settingsFile->flush();
@ -155,7 +168,13 @@ bool ScStwSettings::writeSettingsToFile() {
} }
bool ScStwSettings::loadSettingsFromFile() { bool ScStwSettings::loadSettingsFromFile() {
QJsonDocument doc = QJsonDocument::fromJson(this->settingsFile->readAll()); QJsonParseError error;
QJsonDocument doc = QJsonDocument::fromJson(this->settingsFile->readAll(), &error);
if(error.error != QJsonParseError::NoError) {
qWarning() << "[ERROR][SETTINGS] Error when parsing settings file: " << error.errorString() << " at offset " << error.offset;
return false;
}
if(doc.toVariant().type() != QVariant::Map) if(doc.toVariant().type() != QVariant::Map)
return false; return false;