139 lines
5.4 KiB
C++
139 lines
5.4 KiB
C++
#include "testenv.h"
|
|
#include "fixtures.h"
|
|
|
|
#include "launcherpaths.h"
|
|
#include "localization.h"
|
|
|
|
#include <QJsonArray>
|
|
#include <QSignalSpy>
|
|
|
|
class TestLocalization : public QObject
|
|
{
|
|
Q_OBJECT
|
|
|
|
Localization &loc() { return Localization::instance(); }
|
|
|
|
// Значения каталога напрямую из файла — эталон для сравнения.
|
|
static QJsonObject catalogEntry(const QString &key)
|
|
{
|
|
return Fixtures::readJsonFile(QStringLiteral(BILAUNCHER_SOURCE_DIR "/i18n/translations.json"))
|
|
.value(QStringLiteral("strings"))
|
|
.toObject()
|
|
.value(key)
|
|
.toObject();
|
|
}
|
|
|
|
private slots:
|
|
void init()
|
|
{
|
|
TestEnv::resetLauncherRoot();
|
|
loc().setLanguage(QStringLiteral("en"));
|
|
}
|
|
|
|
void textFollowsLanguage()
|
|
{
|
|
const QJsonObject entry = catalogEntry(QStringLiteral("app.tooltip.openMods"));
|
|
QCOMPARE(Loc::text("app.tooltip.openMods"), entry.value("en").toString());
|
|
|
|
QSignalSpy spy(&loc(), &Localization::languageChanged);
|
|
loc().setLanguage(QStringLiteral("ru"));
|
|
QCOMPARE(spy.count(), 1);
|
|
QCOMPARE(loc().language(), QStringLiteral("ru"));
|
|
QCOMPARE(loc().resolvedLanguage(), QStringLiteral("ru"));
|
|
QCOMPARE(Loc::text("app.tooltip.openMods"), entry.value("ru").toString());
|
|
|
|
// Тот же язык ещё раз — без сигнала.
|
|
loc().setLanguage(QStringLiteral("ru"));
|
|
QCOMPARE(spy.count(), 1);
|
|
}
|
|
|
|
void unknownLanguageFallsBackToSystem()
|
|
{
|
|
QTest::ignoreMessage(QtWarningMsg, QRegularExpression(QStringLiteral("klingon")));
|
|
loc().setLanguage(QStringLiteral("klingon"));
|
|
QCOMPARE(loc().language(), QStringLiteral("system"));
|
|
const QString resolved = loc().resolvedLanguage();
|
|
QVERIFY(resolved == QLatin1String("ru") || resolved == QLatin1String("en"));
|
|
}
|
|
|
|
void missingKeyReturnsKey()
|
|
{
|
|
#ifndef QT_NO_DEBUG
|
|
QTest::ignoreMessage(QtWarningMsg, QRegularExpression(QStringLiteral("no\\.such\\.key")));
|
|
#endif
|
|
QCOMPARE(Loc::text("no.such.key"), QStringLiteral("no.such.key"));
|
|
#ifndef QT_NO_DEBUG
|
|
QTest::ignoreMessage(QtWarningMsg, QRegularExpression(QStringLiteral("no\\.such\\.list")));
|
|
#endif
|
|
QCOMPARE(Loc::list("no.such.list"), QStringList{QStringLiteral("no.such.list")});
|
|
}
|
|
|
|
void listsHaveSameShapeInAllLanguages()
|
|
{
|
|
const QJsonObject strings =
|
|
Fixtures::readJsonFile(QStringLiteral(BILAUNCHER_SOURCE_DIR "/i18n/translations.json"))
|
|
.value(QStringLiteral("strings"))
|
|
.toObject();
|
|
int lists = 0;
|
|
for (auto it = strings.constBegin(); it != strings.constEnd(); ++it) {
|
|
if (!it.value().toObject().value("en").isArray())
|
|
continue;
|
|
++lists;
|
|
const QByteArray key = it.key().toLatin1();
|
|
loc().setLanguage(QStringLiteral("en"));
|
|
const QStringList en = Loc::list(key.constData());
|
|
loc().setLanguage(QStringLiteral("ru"));
|
|
const QStringList ru = Loc::list(key.constData());
|
|
QCOMPARE(en.size(), ru.size());
|
|
QCOMPARE(en.size(), it.value().toObject().value("en").toArray().size());
|
|
}
|
|
if (lists == 0)
|
|
QSKIP("в каталоге нет списков");
|
|
}
|
|
|
|
void availableLanguages()
|
|
{
|
|
const QVariantList languages = loc().availableLanguages();
|
|
QVERIFY(languages.size() >= 3);
|
|
QCOMPARE(languages.first().toMap().value("code").toString(), QStringLiteral("system"));
|
|
QStringList codes;
|
|
for (const QVariant &item : languages)
|
|
codes << item.toMap().value("code").toString();
|
|
QVERIFY(codes.contains("ru"));
|
|
QVERIFY(codes.contains("en"));
|
|
for (const QVariant &item : languages)
|
|
QVERIFY(!item.toMap().value("name").toString().isEmpty());
|
|
}
|
|
|
|
void storedLanguageIsReadOnLoad()
|
|
{
|
|
Fixtures::writeJson(LauncherPaths::settingsFile(), QJsonObject{{"language", "ru"}});
|
|
QVERIFY(loc().load());
|
|
QCOMPARE(loc().language(), QStringLiteral("ru"));
|
|
|
|
Fixtures::writeJson(LauncherPaths::settingsFile(), QJsonObject{{"language", "xx"}});
|
|
QTest::ignoreMessage(QtWarningMsg, QRegularExpression(QStringLiteral("xx")));
|
|
QVERIFY(loc().load());
|
|
QCOMPARE(loc().language(), QStringLiteral("system"));
|
|
|
|
Fixtures::write(LauncherPaths::settingsFile(), "garbage");
|
|
QVERIFY(loc().load());
|
|
QCOMPARE(loc().language(), QStringLiteral("system"));
|
|
}
|
|
|
|
void everyCppKeyExists()
|
|
{
|
|
// Тексты, которые код запрашивает через Loc::text("…"), должны быть в каталоге —
|
|
// иначе пользователь увидит сам ключ. Полная проверка — tools/check_translations.py,
|
|
// здесь — выборка ключей, которыми пользуются тесты.
|
|
for (const char *key : {"storage.error.createFailed", "storage.error.notWritable",
|
|
"java.error.invalidRuntimeId", "version.error.invalidId",
|
|
"launch.error.filesMissing", "auth.offline.error.noNickname"}) {
|
|
QVERIFY2(Loc::text(key) != QLatin1String(key), key);
|
|
}
|
|
}
|
|
};
|
|
|
|
BILAUNCHER_TEST_MAIN(TestLocalization)
|
|
#include "tst_localization.moc"
|