cleanups
This commit is contained in:
@@ -21,9 +21,6 @@ namespace {
|
||||
const QString kManifestUrl =
|
||||
QStringLiteral("https://launchermeta.mojang.com/mc/game/version_manifest_v2.json");
|
||||
|
||||
// Снапшоты выходят примерно раз в неделю, манифест весит около 250 КБ: шесть
|
||||
// часов — это не больше четырёх запросов в сутки, новая версия видна в тот же
|
||||
// день, а десяток открытий списка за сессию не стоит ни одного обращения к сети.
|
||||
constexpr qint64 kCacheTtlSeconds = 6 * 60 * 60;
|
||||
|
||||
constexpr int kTransferTimeoutMs = 20000;
|
||||
@@ -45,13 +42,11 @@ QList<RemoteVersionEntry> parseManifest(const QJsonObject &root)
|
||||
entry.releaseTime = QDateTime::fromString(
|
||||
object.value(QStringLiteral("releaseTime")).toString(), Qt::ISODate);
|
||||
|
||||
// Описание версии качается по этой ссылке, поэтому чужие схемы не берём.
|
||||
if (entry.id.isEmpty() || entry.url.scheme() != QLatin1String("https"))
|
||||
continue;
|
||||
list << entry;
|
||||
}
|
||||
|
||||
// Mojang и так отдаёт новые сверху, но зависеть от этого не стоит.
|
||||
std::stable_sort(list.begin(), list.end(),
|
||||
[](const RemoteVersionEntry &a, const RemoteVersionEntry &b) {
|
||||
if (a.releaseTime != b.releaseTime)
|
||||
@@ -61,7 +56,7 @@ QList<RemoteVersionEntry> parseManifest(const QJsonObject &root)
|
||||
return list;
|
||||
}
|
||||
|
||||
} // namespace
|
||||
}
|
||||
|
||||
VersionManifestService::VersionManifestService(QObject *parent)
|
||||
: QObject(parent)
|
||||
@@ -97,8 +92,6 @@ void VersionManifestService::ensureLoaded(Callback callback, bool forceRefresh)
|
||||
const bool fresh = hasData() && m_fetchedAt.isValid()
|
||||
&& m_fetchedAt.secsTo(QDateTime::currentDateTimeUtc()) < kCacheTtlSeconds;
|
||||
if (!forceRefresh && fresh) {
|
||||
// Колбэк, который то синхронный, то нет, ломает вызывающий код —
|
||||
// на попадании в кэш отвечаем через событийный цикл.
|
||||
if (callback)
|
||||
QTimer::singleShot(0, this, [callback = std::move(callback)] { callback(true, {}); });
|
||||
return;
|
||||
@@ -133,7 +126,6 @@ void VersionManifestService::startRefresh()
|
||||
|
||||
QList<RemoteVersionEntry> parsed =
|
||||
parseManifest(QJsonDocument::fromJson(reply->readAll()).object());
|
||||
// Пустой разбор — испорченный ответ; хороший кэш им не затираем.
|
||||
if (parsed.isEmpty()) {
|
||||
finishRefresh(false, Loc::text("version.error.manifestUnparsable"));
|
||||
return;
|
||||
@@ -152,10 +144,8 @@ void VersionManifestService::finishRefresh(bool ok, const QString &warning)
|
||||
m_refreshing = false;
|
||||
emit refreshingChanged();
|
||||
|
||||
// Колбэк может снова позвать ensureLoaded — список забираем себе заранее.
|
||||
const QList<Callback> pending = std::exchange(m_pending, {});
|
||||
for (const Callback &callback : pending) {
|
||||
// Сеть недоступна, но старые данные есть — работаем на них.
|
||||
if (!ok && hasData())
|
||||
callback(true, warning);
|
||||
else
|
||||
@@ -182,7 +172,6 @@ bool VersionManifestService::readCache()
|
||||
|
||||
void VersionManifestService::writeCache()
|
||||
{
|
||||
// Папку кэша могли удалить уже после запуска лаунчера.
|
||||
if (!LauncherPaths::ensureRootExists())
|
||||
return;
|
||||
|
||||
@@ -196,13 +185,9 @@ void VersionManifestService::writeCache()
|
||||
entry.releaseTime.toString(Qt::ISODate)}};
|
||||
}
|
||||
|
||||
// Своя обёртка: в манифесте Mojang нет отметки времени, по которой можно
|
||||
// судить о свежести кэша.
|
||||
const QJsonObject root{{QStringLiteral("fetchedAt"), m_fetchedAt.toString(Qt::ISODate)},
|
||||
{QStringLiteral("versions"), versions}};
|
||||
|
||||
// QSaveFile: оборванная запись не оставит обрезанный кэш, который потом
|
||||
// пришлось бы отличать от настоящего.
|
||||
QSaveFile file(LauncherPaths::versionManifestFile());
|
||||
if (!file.open(QIODevice::WriteOnly))
|
||||
return;
|
||||
|
||||
Reference in New Issue
Block a user