// OptionsDialog::diffChanged unit tests. Lane GUI. // // Red when a key that didn't actually change starts getting resent to settings.set (it // would still work, but it defeats the fixture's "changed[] names exactly what took // effect" contract and spams event.settings.changed with noise), or a key present in // `current` but absent from `original` stops being treated as changed. #include #include #include #include #include "dialogs/OptionsDialog.hpp" using velox::gui::OptionsDialog; class TstOptionsDialog : public QObject { Q_OBJECT private slots: void identicalValuesProduceNoDiff(); void onlyChangedKeysAreReturned(); void keyAbsentFromOriginalCountsAsChanged(); void allKeysAreNonEmptyAndUnique(); void allKeysMatchesTheSchemaExactly(); }; void TstOptionsDialog::identicalValuesProduceNoDiff() { const QJsonObject original{{"connection.timeoutSec", 30}, {"proxy.mode", "system"}}; const QJsonObject current = original; QVERIFY(OptionsDialog::diffChanged(original, current).isEmpty()); } void TstOptionsDialog::onlyChangedKeysAreReturned() { const QJsonObject original{{"connection.timeoutSec", 30}, {"proxy.mode", "system"}}; const QJsonObject current{{"connection.timeoutSec", 60}, {"proxy.mode", "system"}}; const QJsonObject changed = OptionsDialog::diffChanged(original, current); QCOMPARE(changed.size(), 1); QCOMPARE(changed.value("connection.timeoutSec").toInt(), 60); } void TstOptionsDialog::keyAbsentFromOriginalCountsAsChanged() { const QJsonObject original{{"proxy.mode", "system"}}; const QJsonObject current{{"proxy.mode", "system"}, {"proxy.port", 1080}}; const QJsonObject changed = OptionsDialog::diffChanged(original, current); QCOMPARE(changed.size(), 1); QVERIFY(changed.contains("proxy.port")); } void TstOptionsDialog::allKeysAreNonEmptyAndUnique() { const QStringList keys = OptionsDialog::allKeys(); QVERIFY(!keys.isEmpty()); QCOMPARE(QSet(keys.begin(), keys.end()).size(), keys.size()); } // Red when a key is added to (or removed from) Settings.schema.json without the same // change landing here — either direction is a real bug: an invented key settings.set // would reject with -32602, or a real key the dialog silently never shows. void TstOptionsDialog::allKeysMatchesTheSchemaExactly() { QFile f(QStringLiteral(VELOX_REPO_ROOT "/contracts/schema/types/Settings.schema.json")); QVERIFY2(f.open(QIODevice::ReadOnly), qUtf8Printable(f.errorString())); const QJsonObject schema = QJsonDocument::fromJson(f.readAll()).object(); const QJsonObject properties = schema.value("properties").toObject(); QVERIFY(!properties.isEmpty()); QSet schemaKeys; for (auto it = properties.constBegin(); it != properties.constEnd(); ++it) { schemaKeys.insert(it.key()); } const QStringList dialogKeysList = OptionsDialog::allKeys(); const QSet dialogKeys(dialogKeysList.begin(), dialogKeysList.end()); QCOMPARE(dialogKeys, schemaKeys); } QTEST_MAIN(TstOptionsDialog) #include "tst_optionsdialog.moc"