Merge branch 'fail_concurrent_task' of github.com:Trial97/PrismLauncher into concurrent

Signed-off-by: Trial97 <alexandru.tripon97@gmail.com>
This commit is contained in:
Trial97 2023-10-18 18:08:31 +03:00
commit 30f73a0696
No known key found for this signature in database
GPG Key ID: 55EF5DA53DB36318
17 changed files with 80 additions and 26 deletions

View File

@ -180,7 +180,9 @@ Task::Ptr GetModDependenciesTask::prepareDependencyTask(const ModPlatform::Depen
ResourceAPI::DependencySearchArgs args = { dep, m_version, m_loaderType }; ResourceAPI::DependencySearchArgs args = { dep, m_version, m_loaderType };
ResourceAPI::DependencySearchCallbacks callbacks; ResourceAPI::DependencySearchCallbacks callbacks;
callbacks.on_fail = [](QString reason, int) {
qCritical() << tr("A network error occurred. Could not load project dependenies:%1").arg(reason);
};
callbacks.on_succeed = [dep, provider, pDep, level, this](auto& doc, [[maybe_unused]] auto& pack) { callbacks.on_succeed = [dep, provider, pDep, level, this](auto& doc, [[maybe_unused]] auto& pack) {
try { try {
QJsonArray arr; QJsonArray arr;

View File

@ -149,6 +149,7 @@ void EnsureMetadataTask::executeTask()
if (m_current_task) if (m_current_task)
m_current_task.reset(); m_current_task.reset();
}); });
connect(project_task.get(), &Task::failed, this, &EnsureMetadataTask::emitFailed);
m_current_task = project_task; m_current_task = project_task;
project_task->start(); project_task->start();
@ -159,6 +160,7 @@ void EnsureMetadataTask::executeTask()
if (m_current_task) if (m_current_task)
m_current_task.reset(); m_current_task.reset();
}); });
connect(version_task.get(), &Task::failed, this, &EnsureMetadataTask::emitFailed);
if (m_mods.size() > 1) if (m_mods.size() > 1)
setStatus(tr("Requesting metadata information from %1...").arg(ProviderCaps.readableName(m_provider))); setStatus(tr("Requesting metadata information from %1...").arg(ProviderCaps.readableName(m_provider)));

View File

@ -96,6 +96,7 @@ class ResourceAPI {
}; };
struct VersionSearchCallbacks { struct VersionSearchCallbacks {
std::function<void(QJsonDocument&, ModPlatform::IndexedPack)> on_succeed; std::function<void(QJsonDocument&, ModPlatform::IndexedPack)> on_succeed;
std::function<void(QString const& reason, int network_error_code)> on_fail;
}; };
struct ProjectInfoArgs { struct ProjectInfoArgs {
@ -118,6 +119,7 @@ class ResourceAPI {
struct DependencySearchCallbacks { struct DependencySearchCallbacks {
std::function<void(QJsonDocument&, const ModPlatform::Dependency&)> on_succeed; std::function<void(QJsonDocument&, const ModPlatform::Dependency&)> on_succeed;
std::function<void(QString const& reason, int network_error_code)> on_fail;
}; };
public: public:

View File

@ -119,7 +119,6 @@ void Flame::FileResolvingTask::netJobFinished()
connect(m_checkJob.get(), &NetJob::failed, this, [this, step_progress](QString reason) { connect(m_checkJob.get(), &NetJob::failed, this, [this, step_progress](QString reason) {
step_progress->state = TaskStepState::Failed; step_progress->state = TaskStepState::Failed;
stepProgress(*step_progress); stepProgress(*step_progress);
emitFailed(reason);
}); });
connect(m_checkJob.get(), &NetJob::stepProgress, this, &FileResolvingTask::propagateStepProgress); connect(m_checkJob.get(), &NetJob::stepProgress, this, &FileResolvingTask::propagateStepProgress);
connect(m_checkJob.get(), &NetJob::progress, this, [this, step_progress](qint64 current, qint64 total) { connect(m_checkJob.get(), &NetJob::progress, this, [this, step_progress](qint64 current, qint64 total) {

View File

@ -24,7 +24,7 @@ bool FlameCheckUpdate::abort()
return true; return true;
} }
ModPlatform::IndexedPack getProjectInfo(ModPlatform::IndexedVersion& ver_info) ModPlatform::IndexedPack FlameCheckUpdate::getProjectInfo(ModPlatform::IndexedVersion& ver_info)
{ {
ModPlatform::IndexedPack pack; ModPlatform::IndexedPack pack;
@ -57,6 +57,7 @@ ModPlatform::IndexedPack getProjectInfo(ModPlatform::IndexedVersion& ver_info)
} }
}); });
connect(get_project_job, &NetJob::failed, this, &FlameCheckUpdate::emitFailed);
QObject::connect(get_project_job, &NetJob::finished, [&loop, get_project_job] { QObject::connect(get_project_job, &NetJob::finished, [&loop, get_project_job] {
get_project_job->deleteLater(); get_project_job->deleteLater();
loop.quit(); loop.quit();
@ -68,7 +69,7 @@ ModPlatform::IndexedPack getProjectInfo(ModPlatform::IndexedVersion& ver_info)
return pack; return pack;
} }
ModPlatform::IndexedVersion getFileInfo(int addonId, int fileId) ModPlatform::IndexedVersion FlameCheckUpdate::getFileInfo(int addonId, int fileId)
{ {
ModPlatform::IndexedVersion ver; ModPlatform::IndexedVersion ver;
@ -100,7 +101,7 @@ ModPlatform::IndexedVersion getFileInfo(int addonId, int fileId)
qDebug() << doc; qDebug() << doc;
} }
}); });
connect(get_file_info_job, &NetJob::failed, this, &FlameCheckUpdate::emitFailed);
QObject::connect(get_file_info_job, &NetJob::finished, [&loop, get_file_info_job] { QObject::connect(get_file_info_job, &NetJob::finished, [&loop, get_file_info_job] {
get_file_info_job->deleteLater(); get_file_info_job->deleteLater();
loop.quit(); loop.quit();

View File

@ -22,6 +22,9 @@ class FlameCheckUpdate : public CheckUpdateTask {
void executeTask() override; void executeTask() override;
private: private:
ModPlatform::IndexedPack getProjectInfo(ModPlatform::IndexedVersion& ver_info);
ModPlatform::IndexedVersion getFileInfo(int addonId, int fileId);
NetJob* m_net_job = nullptr; NetJob* m_net_job = nullptr;
bool m_was_aborted = false; bool m_was_aborted = false;

View File

@ -227,6 +227,7 @@ bool FlameCreationTask::updateInstance()
m_files_to_remove.append(old_minecraft_dir.absoluteFilePath(relative_path)); m_files_to_remove.append(old_minecraft_dir.absoluteFilePath(relative_path));
} }
}); });
connect(job.get(), &Task::failed, this, [](QString reason) { qCritical() << "Failed to get files: " << reason; });
connect(job.get(), &Task::finished, &loop, &QEventLoop::quit); connect(job.get(), &Task::finished, &loop, &QEventLoop::quit);
m_process_update_file_info_job = job; m_process_update_file_info_job = job;

View File

@ -323,6 +323,7 @@ void FlamePackExportTask::getProjectsInfo()
} }
buildZip(); buildZip();
}); });
connect(projTask.get(), &Task::failed, this, &FlamePackExportTask::emitFailed);
task.reset(projTask); task.reset(projTask);
task->start(); task->start();
} }

View File

@ -102,6 +102,13 @@ Task::Ptr NetworkResourceAPI::getProjectVersions(VersionSearchArgs&& args, Versi
callbacks.on_succeed(doc, args.pack); callbacks.on_succeed(doc, args.pack);
}); });
QObject::connect(netJob.get(), &NetJob::failed, [&netJob, callbacks](QString reason) {
int network_error_code = -1;
if (auto* failed_action = netJob->getFailedActions().at(0); failed_action && failed_action->m_reply)
network_error_code = failed_action->m_reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt();
callbacks.on_fail(reason, network_error_code);
});
return netJob; return netJob;
} }
@ -146,6 +153,12 @@ Task::Ptr NetworkResourceAPI::getDependencyVersion(DependencySearchArgs&& args,
callbacks.on_succeed(doc, args.dependency); callbacks.on_succeed(doc, args.dependency);
}); });
QObject::connect(netJob.get(), &NetJob::failed, [&netJob, callbacks](QString reason) {
int network_error_code = -1;
if (auto* failed_action = netJob->getFailedActions().at(0); failed_action && failed_action->m_reply)
network_error_code = failed_action->m_reply->attribute(QNetworkRequest::HttpStatusCodeAttribute).toInt();
callbacks.on_fail(reason, network_error_code);
});
return netJob; return netJob;
} }

View File

@ -72,8 +72,6 @@ void ModrinthCheckUpdate::executeTask()
auto response = std::make_shared<QByteArray>(); auto response = std::make_shared<QByteArray>();
auto job = api.latestVersions(hashes, best_hash_type, m_game_versions, m_loaders, response); auto job = api.latestVersions(hashes, best_hash_type, m_game_versions, m_loaders, response);
QEventLoop lock;
connect(job.get(), &Task::succeeded, this, [this, response, &mappings, best_hash_type, job] { connect(job.get(), &Task::succeeded, this, [this, response, &mappings, best_hash_type, job] {
QJsonParseError parse_error{}; QJsonParseError parse_error{};
QJsonDocument doc = QJsonDocument::fromJson(*response, &parse_error); QJsonDocument doc = QJsonDocument::fromJson(*response, &parse_error);
@ -82,7 +80,7 @@ void ModrinthCheckUpdate::executeTask()
<< " reason: " << parse_error.errorString(); << " reason: " << parse_error.errorString();
qWarning() << *response; qWarning() << *response;
failed(parse_error.errorString()); emitFailed(parse_error.errorString());
return; return;
} }
@ -167,19 +165,17 @@ void ModrinthCheckUpdate::executeTask()
m_deps.append(std::make_shared<GetModDependenciesTask::PackDependency>(pack, project_ver)); m_deps.append(std::make_shared<GetModDependenciesTask::PackDependency>(pack, project_ver));
} }
} catch (Json::JsonException& e) { } catch (Json::JsonException& e) {
failed(e.cause() + " : " + e.what()); emitFailed(e.cause() + " : " + e.what());
return;
} }
emitSucceeded();
}); });
connect(job.get(), &Task::finished, &lock, &QEventLoop::quit); connect(job.get(), &Task::failed, this, &ModrinthCheckUpdate::emitFailed);
setStatus(tr("Waiting for the API response from Modrinth...")); setStatus(tr("Waiting for the API response from Modrinth..."));
setProgress(1, 3); setProgress(1, 3);
m_net_job = qSharedPointerObjectCast<NetJob, Task>(job); m_net_job = qSharedPointerObjectCast<NetJob, Task>(job);
job->start(); job->start();
lock.exec();
emitSucceeded();
} }

View File

@ -120,10 +120,10 @@ void ConcurrentTask::executeNextSubTask()
} }
if (m_queue.isEmpty()) { if (m_queue.isEmpty()) {
if (m_doing.isEmpty()) { if (m_doing.isEmpty()) {
// if (m_failed.isEmpty()) if (m_failed.isEmpty())
emitSucceeded(); emitSucceeded();
// else else
// emitFailed(tr("One or more subtasks failed")); emitFailed(tr("One or more subtasks failed"));
} }
return; return;
} }
@ -138,6 +138,7 @@ void ConcurrentTask::startSubTask(Task::Ptr next)
{ {
connect(next.get(), &Task::succeeded, this, [this, next]() { subTaskSucceeded(next); }); connect(next.get(), &Task::succeeded, this, [this, next]() { subTaskSucceeded(next); });
connect(next.get(), &Task::failed, this, [this, next](QString msg) { subTaskFailed(next, msg); }); connect(next.get(), &Task::failed, this, [this, next](QString msg) { subTaskFailed(next, msg); });
// this should never happen but if it does, it's better to fail the task than get stuck
connect(next.get(), &Task::aborted, this, [this, next] { subTaskFailed(next, "Aborted"); }); connect(next.get(), &Task::aborted, this, [this, next] { subTaskFailed(next, "Aborted"); });
connect(next.get(), &Task::status, this, [this, next](QString msg) { subTaskStatus(next, msg); }); connect(next.get(), &Task::status, this, [this, next](QString msg) { subTaskStatus(next, msg); });

View File

@ -326,6 +326,8 @@ auto ModUpdateDialog::ensureMetadata() -> bool
connect(modrinth_task.get(), &EnsureMetadataTask::metadataFailed, [this, &should_try_others](Mod* candidate) { connect(modrinth_task.get(), &EnsureMetadataTask::metadataFailed, [this, &should_try_others](Mod* candidate) {
onMetadataFailed(candidate, should_try_others.find(candidate->internal_id()).value(), ModPlatform::ResourceProvider::MODRINTH); onMetadataFailed(candidate, should_try_others.find(candidate->internal_id()).value(), ModPlatform::ResourceProvider::MODRINTH);
}); });
connect(modrinth_task.get(), &EnsureMetadataTask::failed,
[this](QString reason) { CustomMessageBox::selectable(this, tr("Error"), reason, QMessageBox::Critical)->exec(); });
if (modrinth_task->getHashingTask()) if (modrinth_task->getHashingTask())
seq.addTask(modrinth_task->getHashingTask()); seq.addTask(modrinth_task->getHashingTask());
@ -339,6 +341,8 @@ auto ModUpdateDialog::ensureMetadata() -> bool
connect(flame_task.get(), &EnsureMetadataTask::metadataFailed, [this, &should_try_others](Mod* candidate) { connect(flame_task.get(), &EnsureMetadataTask::metadataFailed, [this, &should_try_others](Mod* candidate) {
onMetadataFailed(candidate, should_try_others.find(candidate->internal_id()).value(), ModPlatform::ResourceProvider::FLAME); onMetadataFailed(candidate, should_try_others.find(candidate->internal_id()).value(), ModPlatform::ResourceProvider::FLAME);
}); });
connect(flame_task.get(), &EnsureMetadataTask::failed,
[this](QString reason) { CustomMessageBox::selectable(this, tr("Error"), reason, QMessageBox::Critical)->exec(); });
if (flame_task->getHashingTask()) if (flame_task->getHashingTask())
seq.addTask(flame_task->getHashingTask()); seq.addTask(flame_task->getHashingTask());
@ -392,6 +396,8 @@ void ModUpdateDialog::onMetadataFailed(Mod* mod, bool try_others, ModPlatform::R
auto task = makeShared<EnsureMetadataTask>(mod, index_dir, next(first_choice)); auto task = makeShared<EnsureMetadataTask>(mod, index_dir, next(first_choice));
connect(task.get(), &EnsureMetadataTask::metadataReady, [this](Mod* candidate) { onMetadataEnsured(candidate); }); connect(task.get(), &EnsureMetadataTask::metadataReady, [this](Mod* candidate) { onMetadataEnsured(candidate); });
connect(task.get(), &EnsureMetadataTask::metadataFailed, [this](Mod* candidate) { onMetadataFailed(candidate, false); }); connect(task.get(), &EnsureMetadataTask::metadataFailed, [this](Mod* candidate) { onMetadataFailed(candidate, false); });
connect(task.get(), &EnsureMetadataTask::failed,
[this](QString reason) { CustomMessageBox::selectable(this, tr("Error"), reason, QMessageBox::Critical)->exec(); });
m_second_try_metadata->addTask(task); m_second_try_metadata->addTask(task);
} else { } else {

View File

@ -207,6 +207,10 @@ void ResourceModel::loadEntry(QModelIndex& entry)
return; return;
versionRequestSucceeded(doc, pack, entry); versionRequestSucceeded(doc, pack, entry);
}; };
if (!callbacks.on_fail)
callbacks.on_fail = [](QString reason, int) {
QMessageBox::critical(nullptr, tr("Error"), tr("A network error occurred. Could not load project versions:%1").arg(reason));
};
if (auto job = m_api->getProjectVersions(std::move(args), std::move(callbacks)); job) if (auto job = m_api->getProjectVersions(std::move(args), std::move(callbacks)); job)
runInfoJob(job); runInfoJob(job);

View File

@ -34,6 +34,7 @@
*/ */
#include "FlamePage.h" #include "FlamePage.h"
#include "ui/dialogs/CustomMessageBox.h"
#include "ui_FlamePage.h" #include "ui_FlamePage.h"
#include <QKeyEvent> #include <QKeyEvent>
@ -193,6 +194,8 @@ void FlamePage::onSelectionChanged(QModelIndex curr, [[maybe_unused]] QModelInde
suggestCurrent(); suggestCurrent();
}); });
QObject::connect(netJob, &NetJob::finished, this, [response, netJob] { netJob->deleteLater(); }); QObject::connect(netJob, &NetJob::finished, this, [response, netJob] { netJob->deleteLater(); });
connect(netJob, &NetJob::failed,
[this](QString reason) { CustomMessageBox::selectable(this, tr("Error"), reason, QMessageBox::Critical)->exec(); });
netJob->start(); netJob->start();
} else { } else {
for (auto version : current.versions) { for (auto version : current.versions) {

View File

@ -35,6 +35,7 @@
*/ */
#include "ModrinthPage.h" #include "ModrinthPage.h"
#include "ui/dialogs/CustomMessageBox.h"
#include "ui_ModrinthPage.h" #include "ui_ModrinthPage.h"
#include "ModrinthModel.h" #include "ModrinthModel.h"
@ -182,6 +183,8 @@ void ModrinthPage::onSelectionChanged(QModelIndex curr, [[maybe_unused]] QModelI
suggestCurrent(); suggestCurrent();
}); });
QObject::connect(netJob, &NetJob::finished, this, [response, netJob] { netJob->deleteLater(); }); QObject::connect(netJob, &NetJob::finished, this, [response, netJob] { netJob->deleteLater(); });
connect(netJob, &NetJob::failed,
[this](QString reason) { CustomMessageBox::selectable(this, tr("Error"), reason, QMessageBox::Critical)->exec(); });
netJob->start(); netJob->start();
} else } else
updateUI(); updateUI();
@ -235,6 +238,8 @@ void ModrinthPage::onSelectionChanged(QModelIndex curr, [[maybe_unused]] QModelI
suggestCurrent(); suggestCurrent();
}); });
QObject::connect(netJob, &NetJob::finished, this, [response, netJob] { netJob->deleteLater(); }); QObject::connect(netJob, &NetJob::finished, this, [response, netJob] { netJob->deleteLater(); });
connect(netJob, &NetJob::failed,
[this](QString reason) { CustomMessageBox::selectable(this, tr("Error"), reason, QMessageBox::Critical)->exec(); });
netJob->start(); netJob->start();
} else { } else {

View File

@ -34,6 +34,7 @@
*/ */
#include "TechnicPage.h" #include "TechnicPage.h"
#include "ui/dialogs/CustomMessageBox.h"
#include "ui/widgets/ProjectItem.h" #include "ui/widgets/ProjectItem.h"
#include "ui_TechnicPage.h" #include "ui_TechnicPage.h"
@ -208,6 +209,8 @@ void TechnicPage::suggestCurrent()
metadataLoaded(); metadataLoaded();
}); });
connect(jobPtr.get(), &NetJob::failed,
[this](QString reason) { CustomMessageBox::selectable(this, tr("Error"), reason, QMessageBox::Critical)->exec(); });
jobPtr = netJob; jobPtr = netJob;
jobPtr->start(); jobPtr->start();
@ -258,6 +261,8 @@ void TechnicPage::metadataLoaded()
netJob->addNetAction(Net::ApiDownload::makeByteArray(QUrl(url), response)); netJob->addNetAction(Net::ApiDownload::makeByteArray(QUrl(url), response));
QObject::connect(netJob.get(), &NetJob::succeeded, this, &TechnicPage::onSolderLoaded); QObject::connect(netJob.get(), &NetJob::succeeded, this, &TechnicPage::onSolderLoaded);
connect(jobPtr.get(), &NetJob::failed,
[this](QString reason) { CustomMessageBox::selectable(this, tr("Error"), reason, QMessageBox::Critical)->exec(); });
jobPtr = netJob; jobPtr = netJob;
jobPtr->start(); jobPtr->start();

View File

@ -102,14 +102,7 @@ void VariableSizedImageObject::loadImage(QTextDocument* doc, const QUrl& source,
auto full_entry_path = entry->getFullPath(); auto full_entry_path = entry->getFullPath();
auto source_url = source; auto source_url = source;
connect(job, &NetJob::succeeded, this, [this, doc, full_entry_path, source_url, posInDocument] { auto loadImage = [this, doc, full_entry_path, source_url, posInDocument](const QImage& image) {
qDebug() << "Loaded resource at" << full_entry_path;
// If we flushed, don't proceed.
if (!m_fetching_images.contains(source_url))
return;
QImage image(full_entry_path);
doc->addResource(QTextDocument::ImageResource, source_url, image); doc->addResource(QTextDocument::ImageResource, source_url, image);
parseImage(doc, image, posInDocument); parseImage(doc, image, posInDocument);
@ -121,6 +114,23 @@ void VariableSizedImageObject::loadImage(QTextDocument* doc, const QUrl& source,
doc->setPageSize(size); doc->setPageSize(size);
m_fetching_images.remove(source_url); m_fetching_images.remove(source_url);
};
connect(job, &NetJob::succeeded, this, [this, full_entry_path, source_url, loadImage] {
qDebug() << "Loaded resource at:" << full_entry_path;
// If we flushed, don't proceed.
if (!m_fetching_images.contains(source_url))
return;
QImage image(full_entry_path);
loadImage(image);
});
connect(job, &NetJob::failed, this, [this, full_entry_path, source_url, loadImage](QString reason) {
qWarning() << "Failed resource at:" << full_entry_path << " because:" << reason;
// If we flushed, don't proceed.
if (!m_fetching_images.contains(source_url))
return;
loadImage(QImage());
}); });
connect(job, &NetJob::finished, job, &NetJob::deleteLater); connect(job, &NetJob::finished, job, &NetJob::deleteLater);