132 lines
3.2 KiB
C++
132 lines
3.2 KiB
C++
#include "common.hpp"
|
|
|
|
#include "node.hpp"
|
|
|
|
using Qt::StringLiterals::operator""_s;
|
|
|
|
namespace ZShell::settings {
|
|
|
|
Q_LOGGING_CATEGORY(lcSettings, "zshell.settings", QtInfoMsg)
|
|
|
|
WriteScope::WriteScope(Node* node, WriteOrigin origin)
|
|
: m_root(node->rootNode()), m_previous(m_root->m_writeOrigin) {
|
|
m_root->m_writeOrigin = origin;
|
|
}
|
|
|
|
WriteScope::~WriteScope() {
|
|
m_root->m_writeOrigin = m_previous;
|
|
}
|
|
|
|
InternalRead::InternalRead(Node* node)
|
|
: m_root(node->rootNode()), m_previous(m_root->m_internalRead) {
|
|
m_root->m_internalRead = true;
|
|
}
|
|
|
|
InternalRead::~InternalRead() {
|
|
m_root->m_internalRead = m_previous;
|
|
}
|
|
|
|
QString DiagnosticType::toString(Type t) {
|
|
switch (t) {
|
|
case UnknownOption:
|
|
return u"UnknownOption"_s;
|
|
case GlobalOption:
|
|
return u"GlobalOption"_s;
|
|
case TypeMismatch:
|
|
return u"TypeMismatch"_s;
|
|
case InvalidValue:
|
|
return u"InvalidValue"_s;
|
|
}
|
|
|
|
Q_UNREACHABLE_RETURN(QString());
|
|
}
|
|
|
|
namespace {
|
|
|
|
QString expectedStr(ExpectedType expected) {
|
|
switch (expected) {
|
|
case ExpectedType::Bool:
|
|
return QStringLiteral("a boolean");
|
|
case ExpectedType::Int:
|
|
return QStringLiteral("an integer");
|
|
case ExpectedType::Real:
|
|
return QStringLiteral("a number");
|
|
case ExpectedType::String:
|
|
return QStringLiteral("a string");
|
|
case ExpectedType::Array:
|
|
return QStringLiteral("an array");
|
|
case ExpectedType::Object:
|
|
return QStringLiteral("an object");
|
|
}
|
|
|
|
Q_UNREACHABLE_RETURN(QString());
|
|
}
|
|
|
|
QString receivedStr(const QJsonValue& value) {
|
|
switch (value.type()) {
|
|
case QJsonValue::Null:
|
|
return QStringLiteral("null");
|
|
case QJsonValue::Bool:
|
|
return QStringLiteral("a boolean");
|
|
case QJsonValue::Double:
|
|
return QStringLiteral("a number");
|
|
case QJsonValue::String:
|
|
return QStringLiteral("a string");
|
|
case QJsonValue::Array:
|
|
return QStringLiteral("an array");
|
|
case QJsonValue::Object:
|
|
return QStringLiteral("an object");
|
|
default:
|
|
return QStringLiteral("nothing");
|
|
}
|
|
}
|
|
|
|
QString mismatchStr(
|
|
const QList<ExpectedType>& expected, const QJsonValue& value) {
|
|
QStringList types;
|
|
types.reserve(expected.size());
|
|
for (const auto type : expected)
|
|
types << expectedStr(type);
|
|
const auto received = receivedStr(value);
|
|
|
|
switch (expected.size()) {
|
|
case 2:
|
|
return QStringLiteral("Expected %1 or %2, got %3")
|
|
.arg(types[0], types[1], received);
|
|
case 3:
|
|
return QStringLiteral("Expected %1, %2 or %3, got %4")
|
|
.arg(types[0], types[1], types[2], received);
|
|
case 4:
|
|
return QStringLiteral("Expected one of: %1, %2, %3, %4; got %5")
|
|
.arg(types[0], types[1], types[2], types[3], received);
|
|
default:
|
|
// The bounds are checked in macros.hpp `unionType<...T>`
|
|
Q_UNREACHABLE_RETURN(QString());
|
|
}
|
|
}
|
|
|
|
} // namespace
|
|
|
|
Diagnostic Diagnostic::mismatch(
|
|
ExpectedType expected, const QJsonValue& value, const QString& option) {
|
|
return {
|
|
.type = DiagnosticType::TypeMismatch,
|
|
.option = option,
|
|
.message = QStringLiteral("Expected %1, got %2")
|
|
.arg(expectedStr(expected), receivedStr(value)),
|
|
};
|
|
}
|
|
|
|
Diagnostic Diagnostic::mismatch(
|
|
const QList<ExpectedType>& expected,
|
|
const QJsonValue& value,
|
|
const QString& option) {
|
|
return {
|
|
.type = DiagnosticType::TypeMismatch,
|
|
.option = option,
|
|
.message = mismatchStr(expected, value),
|
|
};
|
|
}
|
|
|
|
} // namespace ZShell::settings
|