URL protocol modpack import for any encoded URL (#4990)

This commit is contained in:
Alexandru Ionut Tripon 2026-02-22 21:58:08 +00:00 committed by GitHub
commit 4ed77a940c
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
2 changed files with 83 additions and 1 deletions

View file

@ -48,6 +48,7 @@
#include <QDir>
#include <QFileInfo>
#include <QUrl>
#include <QUrlQuery>
#include <QVariant>
#include <QAction>
@ -940,6 +941,11 @@ void MainWindow::processURLs(QList<QUrl> urls)
QMap<QString, QString> extra_info;
QUrl local_url;
if (!url.isLocalFile()) { // download the remote resource and identify
const bool isExternalURLImport =
(url.host().toLower() == "import") ||
(url.path().startsWith("/import", Qt::CaseInsensitive));
QUrl dl_url;
if (url.scheme() == "curseforge") {
// need to find the download link for the modpack / resource
@ -993,7 +999,7 @@ void MainWindow::processURLs(QList<QUrl> urls)
dlUrlDialod.execWithTask(job.get());
}
} else if (url.scheme() == BuildConfig.LAUNCHER_APP_BINARY_NAME) {
} else if (url.scheme() == BuildConfig.LAUNCHER_APP_BINARY_NAME && !isExternalURLImport) {
QVariantMap receivedData;
const QUrlQuery query(url.query());
const auto items = query.queryItems();
@ -1001,6 +1007,78 @@ void MainWindow::processURLs(QList<QUrl> urls)
receivedData.insert(it->first, it->second);
emit APPLICATION->oauthReplyRecieved(receivedData);
continue;
} else if ((url.scheme() == "prismlauncher" || url.scheme() == BuildConfig.LAUNCHER_APP_BINARY_NAME)
&& isExternalURLImport) {
// PrismLauncher URL protocol modpack import
// works for any prism fork
// preferred import format: prismlauncher://import?url=ENCODED
const auto host = url.host().toLower();
const auto path = url.path();
QString encodedTarget;
{
QUrlQuery query(url);
const auto values = query.allQueryItemValues("url");
if (!values.isEmpty()) {
encodedTarget = values.first();
}
}
// alternative import format: prismlauncher://import/ENCODED
if (encodedTarget.isEmpty()) {
QString p = path;
if (p.startsWith("/import/", Qt::CaseInsensitive)) {
p = p.mid(QString("/import/").size());
} else if (host == "import" && p.startsWith("/")) {
p = p.mid(1);
}
if (!p.isEmpty() && p != "/import") {
encodedTarget = p;
}
}
if (encodedTarget.isEmpty()) {
CustomMessageBox::selectable(
this,
tr("Error"),
tr("Invalid import link: missing 'url' parameter."),
QMessageBox::Critical
)->show();
continue;
}
const QString decodedStr = QUrl::fromPercentEncoding(encodedTarget.toUtf8()).trimmed();
QUrl target = QUrl::fromUserInput(decodedStr);
// Validate: only allow http(s)
if (!target.isValid() || (target.scheme() != "https" && target.scheme() != "http")) {
CustomMessageBox::selectable(
this,
tr("Error"),
tr("Invalid import link: URL must be http(s)."),
QMessageBox::Critical
)->show();
continue;
}
const auto res = QMessageBox::question(
this,
tr("Install modpack"),
tr("Do you want to download and import a modpack from:\n%1\n\nURL:\n%2")
.arg(target.host(), target.toString()),
QMessageBox::Yes | QMessageBox::No,
QMessageBox::Yes
);
if (res != QMessageBox::Yes) {
continue;
}
dl_url = target;
} else {
dl_url = url;
}

View file

@ -397,6 +397,10 @@ Section "@Launcher_DisplayName@"
WriteRegStr HKCU Software\Classes\@Launcher_APP_BINARY_NAME@ "URL Protocol" ""
WriteRegStr HKCU Software\Classes\@Launcher_APP_BINARY_NAME@\shell\open\command "" '"$INSTDIR\@Launcher_APP_BINARY_NAME@.exe" "%1"'
; Write the URL Handler into registry for prismlauncher import
WriteRegStr HKCU Software\Classes\prismlauncher "URL Protocol" ""
WriteRegStr HKCU Software\Classes\prismlauncher\shell\open\command "" '"$INSTDIR\@Launcher_APP_BINARY_NAME@.exe" "%1"'
; Write the uninstall keys for Windows
; https://learn.microsoft.com/en-us/windows/win32/msi/uninstall-registry-key
${GetParameters} $R0