diff --git a/src/cmd/cmd.cpp b/src/cmd/cmd.cpp index 293a65078ab..afab62d06e2 100644 --- a/src/cmd/cmd.cpp +++ b/src/cmd/cmd.cpp @@ -485,7 +485,7 @@ int main(int argc, char **argv) .value(QStringLiteral("capabilities")) .toObject(); qDebug() << "Server capabilities" << caps; - ctx.account->setCapabilities(caps.toVariantMap()); + ctx.account->setCapabilities({ctx.account->url(), caps.toVariantMap()}); switch (ctx.account->serverSupportLevel()) { case Account::ServerSupportLevel::Supported: diff --git a/src/gui/accountmanager.cpp b/src/gui/accountmanager.cpp index 8422e850707..11a1c97dd73 100644 --- a/src/gui/accountmanager.cpp +++ b/src/gui/accountmanager.cpp @@ -285,7 +285,7 @@ AccountPtr AccountManager::loadAccountHelper(QSettings &settings) acc->_davUser = settings.value(davUserC()).toString(); acc->_displayName = settings.value(davUserDisplyNameC()).toString(); - acc->setCapabilities(settings.value(capabilitesC()).value()); + acc->setCapabilities({acc->url(), settings.value(capabilitesC()).value()}); acc->setDefaultSyncRoot(settings.value(defaultSyncRootC()).toString()); // We want to only restore settings for that auth type and the user value diff --git a/src/gui/fetchserversettings.cpp b/src/gui/fetchserversettings.cpp index 7fe03765180..96ba0261db6 100644 --- a/src/gui/fetchserversettings.cpp +++ b/src/gui/fetchserversettings.cpp @@ -56,7 +56,7 @@ void FetchServerSettingsJob::start() if (auto reply = job->reply()) { _account->setHttp2Supported(reply->attribute(QNetworkRequest::Http2WasUsedAttribute).toBool()); } - _account->setCapabilities(caps.toVariantMap()); + _account->setCapabilities({_account->url(), caps.toVariantMap()}); if (checkServerInfo()) { auto *userJob = new JsonApiJob(_account, QStringLiteral("ocs/v2.php/cloud/user"), SimpleNetworkJob::UrlQuery{}, QNetworkRequest{}, this); job->setAuthenticationJob(isAuthJob()); @@ -98,7 +98,7 @@ void FetchServerSettingsJob::runAsyncUpdates() }; if (_account->capabilities().appProviders().enabled) { - auto *jsonJob = new JsonJob(_account, _account->url(), _account->capabilities().appProviders().appsUrl, "GET"); + auto *jsonJob = new JsonJob(_account, _account->capabilities().appProviders().appsUrl, {}, "GET"); connect(jsonJob, &JsonJob::finishedSignal, this, [jsonJob, this] { _account->setAppProvider(AppProvider{jsonJob->data()}); }); jsonJob->start(); } diff --git a/src/libsync/account.cpp b/src/libsync/account.cpp index 3240dd65386..a53921ab4b2 100644 --- a/src/libsync/account.cpp +++ b/src/libsync/account.cpp @@ -61,7 +61,7 @@ QString Account::commonCacheDirectory() Account::Account(const QUuid &uuid, QObject *parent) : QObject(parent) , _uuid(uuid) - , _capabilities(QVariantMap()) + , _capabilities({}, {}) , _jobQueue(this) , _queueGuard(&_jobQueue) , _credentialManager(new CredentialManager(this)) diff --git a/src/libsync/appprovider.cpp b/src/libsync/appprovider.cpp index a7f6883d593..9afd1cd07a6 100644 --- a/src/libsync/appprovider.cpp +++ b/src/libsync/appprovider.cpp @@ -78,7 +78,7 @@ bool AppProvider::open(const AccountPtr &account, const QString &localPath, cons const auto &a = app(localPath); if (a.isValid()) { SimpleNetworkJob::UrlQuery query { { QStringLiteral("file_id"), QString::fromUtf8(fileId) } }; - auto *job = new JsonJob(account, account->url(), account->capabilities().appProviders().openWebUrl, "POST", query); + auto *job = new JsonJob(account, account->capabilities().appProviders().openWebUrl, {}, "POST", query); QObject::connect(job, &JsonJob::finishedSignal, [account, job, localPath] { if (job->httpStatusCode() == 200) { const auto url = QUrl(job->data().value(QStringLiteral("uri")).toString()); diff --git a/src/libsync/capabilities.cpp b/src/libsync/capabilities.cpp index 9a722683d98..4e827cad3f6 100644 --- a/src/libsync/capabilities.cpp +++ b/src/libsync/capabilities.cpp @@ -14,15 +14,15 @@ #include "capabilities.h" -#include #include +#include using namespace std::chrono; namespace OCC { -Capabilities::Capabilities(const QVariantMap &capabilities) +Capabilities::Capabilities(const QUrl &url, const QVariantMap &capabilities) : _capabilities(capabilities) , _fileSharingCapabilities(_capabilities.value(QStringLiteral("files_sharing")).toMap()) , _fileSharingPublicCapabilities(_fileSharingCapabilities.value(QStringLiteral("public"), {}).toMap()) @@ -30,7 +30,7 @@ Capabilities::Capabilities(const QVariantMap &capabilities) , _spaces(_capabilities.value(QStringLiteral("spaces")).toMap()) , _status(_capabilities.value(QStringLiteral("core")).toMap().value(QStringLiteral("status")).toMap()) , _appProviders(AppProviders::findVersion( - _capabilities.value(QStringLiteral("files")).toMap().value(QStringLiteral("app_providers")).toList(), QVersionNumber({1, 1, 0}))) + url, _capabilities.value(QStringLiteral("files")).toMap().value(QStringLiteral("app_providers")).toList(), QVersionNumber({1, 1, 0}))) , _filesSharing(_fileSharingCapabilities) , _migration(_capabilities.value(QStringLiteral("migration")).toMap()) { @@ -313,28 +313,28 @@ bool SpaceSupport::isValid() const return !version.isNull(); } -Capabilities::AppProviders::AppProviders(const QVariantMap &appProviders) +Capabilities::AppProviders::AppProviders(const QUrl &baseUrl, const QVariantMap &appProviders) : enabled(appProviders.value(QStringLiteral("enabled")).toBool()) , version(QVersionNumber::fromString(appProviders.value(QStringLiteral("version")).toString())) - , appsUrl(appProviders.value(QStringLiteral("apps_url")).toString()) - , openUrl(appProviders.value(QStringLiteral("open_url")).toString()) - , newUrl(appProviders.value(QStringLiteral("new_url")).toString()) - , openWebUrl(appProviders.value(QStringLiteral("open_web_url")).toString()) + , appsUrl(baseUrl.resolved(appProviders.value(QStringLiteral("apps_url")).toUrl())) + , openUrl(baseUrl.resolved(appProviders.value(QStringLiteral("open_url")).toUrl())) + , newUrl(baseUrl.resolved(appProviders.value(QStringLiteral("new_url")).toUrl())) + , openWebUrl(baseUrl.resolved(appProviders.value(QStringLiteral("open_web_url")).toUrl())) { } + const Capabilities::AppProviders &Capabilities::appProviders() const { return _appProviders; } -Capabilities::AppProviders Capabilities::AppProviders::findVersion(const QVariantList &list, const QVersionNumber &v) +Capabilities::AppProviders Capabilities::AppProviders::findVersion(const QUrl &baseUrl, const QVariantList &list, const QVersionNumber &v) { auto it = std::find_if(list.cbegin(), list.cend(), [&v](const auto &it) { return QVersionNumber::fromString(it.toMap().value(QStringLiteral("version")).toString()) == v; }); - return it != list.cend() ? Capabilities::AppProviders { it->toMap() } - : Capabilities::AppProviders(); + return it != list.cend() ? Capabilities::AppProviders{baseUrl, it->toMap()} : Capabilities::AppProviders{}; } const FilesSharing &Capabilities::filesSharing() const diff --git a/src/libsync/capabilities.h b/src/libsync/capabilities.h index f44e0b27327..d431f648916 100644 --- a/src/libsync/capabilities.h +++ b/src/libsync/capabilities.h @@ -144,19 +144,19 @@ class OWNCLOUDSYNC_EXPORT Capabilities } */ AppProviders() = default; - static AppProviders findVersion(const QVariantList &list, const QVersionNumber &v); - AppProviders(const QVariantMap &appProviders); + static AppProviders findVersion(const QUrl &baseUrl, const QVariantList &list, const QVersionNumber &v); + AppProviders(const QUrl &baseUrl, const QVariantMap &appProviders); bool enabled = false; QVersionNumber version; - QString appsUrl; - QString openUrl; - QString newUrl; - QString openWebUrl; + QUrl appsUrl; + QUrl openUrl; + QUrl newUrl; + QUrl openWebUrl; }; - Capabilities(const QVariantMap &capabilities); + Capabilities(const QUrl &url, const QVariantMap &capabilities); bool shareAPI() const; bool sharePublicLink() const; diff --git a/test/testlocaldiscovery.cpp b/test/testlocaldiscovery.cpp index fc28df99b74..e21982a2b3b 100644 --- a/test/testlocaldiscovery.cpp +++ b/test/testlocaldiscovery.cpp @@ -226,7 +226,7 @@ private slots: auto cap = TestUtils::testCapabilities(); cap.insert( {{QStringLiteral("files"), QVariantMap{{QStringLiteral("blacklisted_files"), QVariantList{QStringLiteral(".foo"), QStringLiteral("bar")}}}}}); - fakeFolder.account()->setCapabilities(cap); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), cap}); fakeFolder.localModifier().insert(QStringLiteral("C/.foo")); fakeFolder.localModifier().insert(QStringLiteral("C/bar")); fakeFolder.localModifier().insert(QStringLiteral("C/moo")); diff --git a/test/testspacesmigration/testspacesmigration.cpp b/test/testspacesmigration/testspacesmigration.cpp index 8bb5062c3ee..bdf229d2e5a 100644 --- a/test/testspacesmigration/testspacesmigration.cpp +++ b/test/testspacesmigration/testspacesmigration.cpp @@ -52,7 +52,7 @@ private slots: auto cap = TestUtils::testCapabilities(); cap[QStringLiteral("migration")] = QVariantMap{{QStringLiteral("space_migration"), QVariantMap{{QStringLiteral("enabled"), true}, {QStringLiteral("endpoint"), QStringLiteral("migration/spaces")}}}}; - fakeFolder.account()->setCapabilities(cap); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), cap}); const QUrl personalUrl( diff --git a/test/testsyncconflict.cpp b/test/testsyncconflict.cpp index df098d20186..83f80bdab46 100644 --- a/test/testsyncconflict.cpp +++ b/test/testsyncconflict.cpp @@ -134,7 +134,7 @@ private slots: QFETCH_GLOBAL(bool, filesAreDehydrated); FakeFolder fakeFolder(FileInfo::A12_B12_C12_S12(), vfsMode, filesAreDehydrated); - fakeFolder.account()->setCapabilities(uploadConflictFilesCapabilities(true)); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), uploadConflictFilesCapabilities(true)}); QCOMPARE(fakeFolder.currentLocalState(), fakeFolder.currentRemoteState()); QMap conflictMap; @@ -194,7 +194,7 @@ private slots: QFETCH_GLOBAL(bool, filesAreDehydrated); FakeFolder fakeFolder(FileInfo::A12_B12_C12_S12(), vfsMode, filesAreDehydrated); - fakeFolder.account()->setCapabilities(uploadConflictFilesCapabilities(true)); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), uploadConflictFilesCapabilities(true)}); QCOMPARE(fakeFolder.currentLocalState(), fakeFolder.currentRemoteState()); QMap conflictMap; @@ -269,7 +269,7 @@ private slots: QFETCH_GLOBAL(bool, filesAreDehydrated); FakeFolder fakeFolder(FileInfo::A12_B12_C12_S12(), vfsMode, filesAreDehydrated); - fakeFolder.account()->setCapabilities(uploadConflictFilesCapabilities(true)); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), uploadConflictFilesCapabilities(true)}); QCOMPARE(fakeFolder.currentLocalState(), fakeFolder.currentRemoteState()); // With no headers from the server @@ -321,7 +321,7 @@ private slots: QFETCH_GLOBAL(bool, filesAreDehydrated); FakeFolder fakeFolder(FileInfo::A12_B12_C12_S12(), vfsMode, filesAreDehydrated); - fakeFolder.account()->setCapabilities(uploadConflictFilesCapabilities(true)); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), uploadConflictFilesCapabilities(true)}); QCOMPARE(fakeFolder.currentLocalState(), fakeFolder.currentRemoteState()); // Make conflict records @@ -352,7 +352,7 @@ private slots: QFETCH_GLOBAL(bool, filesAreDehydrated); FakeFolder fakeFolder(FileInfo::A12_B12_C12_S12(), vfsMode, filesAreDehydrated); - fakeFolder.account()->setCapabilities(uploadConflictFilesCapabilities(false)); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), uploadConflictFilesCapabilities(false)}); QCOMPARE(fakeFolder.currentLocalState(), fakeFolder.currentRemoteState()); // Create two conflicts @@ -478,7 +478,7 @@ private slots: QFETCH_GLOBAL(bool, filesAreDehydrated); FakeFolder fakeFolder(FileInfo::A12_B12_C12_S12(), vfsMode, filesAreDehydrated); - fakeFolder.account()->setCapabilities(uploadConflictFilesCapabilities(true)); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), uploadConflictFilesCapabilities(true)}); ItemCompletedSpy completeSpy(fakeFolder); auto cleanup = [&]() { @@ -563,7 +563,7 @@ private slots: QFETCH_GLOBAL(bool, filesAreDehydrated); FakeFolder fakeFolder(FileInfo::A12_B12_C12_S12(), vfsMode, filesAreDehydrated); - fakeFolder.account()->setCapabilities(uploadConflictFilesCapabilities(true)); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), uploadConflictFilesCapabilities(true)}); ItemCompletedSpy completeSpy(fakeFolder); // 1) a NEW/NEW conflict diff --git a/test/testsyncengine.cpp b/test/testsyncengine.cpp index bb4931354a5..369f6c6d020 100644 --- a/test/testsyncengine.cpp +++ b/test/testsyncengine.cpp @@ -151,7 +151,7 @@ private slots: QFETCH_GLOBAL(bool, filesAreDehydrated); FakeFolder fakeFolder(FileInfo {}, vfsMode, filesAreDehydrated); - fakeFolder.account()->setCapabilities(TestUtils::testCapabilities(CheckSums::Algorithm::SHA1)); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), TestUtils::testCapabilities(CheckSums::Algorithm::SHA1)}); fakeFolder.localModifier().insert(QStringLiteral("a1.eml"), 64_b, 'A'); fakeFolder.localModifier().insert(QStringLiteral("a2.eml"), 64_b, 'A'); fakeFolder.localModifier().insert(QStringLiteral("a3.eml"), 64_b, 'A'); @@ -713,7 +713,7 @@ private slots: cap[QStringLiteral("dav")] = dav; return cap; }; - fakeFolder.syncEngine().account()->setCapabilities(invalidFilenameRegexCapabilities(QStringLiteral("my[fgh]ile"))); + fakeFolder.syncEngine().account()->setCapabilities({fakeFolder.account()->url(), invalidFilenameRegexCapabilities(QStringLiteral("my[fgh]ile"))}); fakeFolder.localModifier().insert(QStringLiteral("C/myfile.txt")); QVERIFY(fakeFolder.applyLocalModificationsAndSync()); QVERIFY(!fakeFolder.currentRemoteState().find(QStringLiteral("C/myfile.txt"))); @@ -763,7 +763,7 @@ private slots: auto cap = TestUtils::testCapabilities(); // unset chunking v1 cap.remove(QStringLiteral("dav")); - fakeFolder.account()->setCapabilities(cap); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), cap}); auto counter = std::make_unique(); fakeFolder.setServerOverride([counter = counter.get(), fakeFolder = &fakeFolder]( diff --git a/test/testsyncmove.cpp b/test/testsyncmove.cpp index 15654f980a9..737903ae8b4 100644 --- a/test/testsyncmove.cpp +++ b/test/testsyncmove.cpp @@ -173,7 +173,7 @@ private slots: QFETCH_GLOBAL(bool, filesAreDehydrated); FakeFolder fakeFolder(FileInfo::A12_B12_C12_S12(), vfsMode, filesAreDehydrated); - fakeFolder.account()->setCapabilities(TestUtils::testCapabilities(CheckSums::Algorithm::ADLER32)); + fakeFolder.account()->setCapabilities({fakeFolder.account()->url(), TestUtils::testCapabilities(CheckSums::Algorithm::ADLER32)}); OperationCounter counter(fakeFolder); diff --git a/test/testuploadreset.cpp b/test/testuploadreset.cpp index 110d0ba60ed..757e1ba61ae 100644 --- a/test/testuploadreset.cpp +++ b/test/testuploadreset.cpp @@ -52,7 +52,7 @@ private slots: cap[QStringLiteral("dav")] = dav; return cap; }; - fakeFolder.syncEngine().account()->setCapabilities(httpErrorCodesThatResetFailingChunkedUploadsCapabilities({ 500 })); + fakeFolder.syncEngine().account()->setCapabilities({fakeFolder.account()->url(), httpErrorCodesThatResetFailingChunkedUploadsCapabilities({500})}); const auto size = 100_mb; // 100 MB fakeFolder.localModifier().insert(QStringLiteral("A/a0"), size); diff --git a/test/testutils/testutils.cpp b/test/testutils/testutils.cpp index 742cb64c9f1..e46fb70d6df 100644 --- a/test/testutils/testutils.cpp +++ b/test/testutils/testutils.cpp @@ -35,7 +35,7 @@ namespace TestUtils { acc->setCredentials(cred); acc->setUrl(QUrl(QStringLiteral("http://localhost/owncloud"))); acc->setDavDisplayName(QStringLiteral("fakename") + acc->uuid().toString(QUuid::WithoutBraces)); - acc->setCapabilities(OCC::TestUtils::testCapabilities()); + acc->setCapabilities({acc->url(), OCC::TestUtils::testCapabilities()}); return {OCC::AccountManager::instance()->addAccount(acc).get(), &TestUtilsPrivate::accountStateDeleter}; }