Server: Parse version from capabilities too #5691 (#5698)
authorMarkus Goetz <markus@woboq.com>
Wed, 19 Apr 2017 09:02:03 +0000 (11:02 +0200)
committerckamm <mail@ckamm.de>
Wed, 19 Apr 2017 09:02:03 +0000 (11:02 +0200)
Newer servers will have the option of hiding version, versionstring, edition
and productname. They will always send the full information in the capabilities.

src/gui/creds/httpcredentialsgui.cpp
src/gui/owncloudsetupwizard.cpp
src/libsync/account.h
src/libsync/connectionvalidator.cpp
src/libsync/connectionvalidator.h
src/libsync/networkjobs.cpp

index 8eb5c40ee6ad2e1fa811648de598a1448aacdcbf..dbfce816943cf24a12fa544b705d155b45b1efe4 100644 (file)
@@ -70,17 +70,19 @@ void HttpCredentialsGui::askFromUserAsync()
 
 QString HttpCredentialsGui::requestAppPasswordText(const Account* account)
 {
-    if (account->serverVersionInt() < Account::makeServerVersion(9, 1, 0)) {
-        // Older server than 9.1 does not have the feature to request App Password
-        return QString();
-    }
-
+    int version = account->serverVersionInt();
     QString path;
-    if (account->serverVersionInt() < Account::makeServerVersion(10, 0, 0)) {
+
+    // Version may not be available before login on new servers!
+    if (!version || version >= Account::makeServerVersion(10, 0, 0)) {
+        path = QLatin1String("/index.php/settings/personal?sectionid=security#apppasswords");
+    } else if (version >= Account::makeServerVersion(9, 1, 0)) {
         path = QLatin1String("/index.php/settings/personal?section=apppasswords");
     } else {
-        path = QLatin1String("/index.php/settings/personal?sectionid=security#apppasswords");
+        // Older server than 9.1 does not have the feature to request App Password
+        return QString();
     }
+
     return tr("<a href=\"%1\">Click here</a> to request an app password from the web interface.")
         .arg(account->url().toString() + path);
 }
index 933d36bd832db0f4161d9784abf3b5c4d0bc2218..971ccf827b991e5e1596c2aed852934b8823ec66 100644 (file)
@@ -183,6 +183,8 @@ void OwncloudSetupWizard::slotOwnCloudFoundAuth(const QUrl& url, const QVariantM
                                              Utility::escape(CheckServerJob::versionString(info)),
                                              Utility::escape(serverVersion)));
 
+    // Note with newer servers we get the version actually only later in capabilities
+    // https://github.com/owncloud/core/pull/27473/files
     _ocWizard->account()->setServerVersion(serverVersion);
 
     QString p = url.path();
index e081121b3f6bbe37f99a4ef0331f5d0ecd75fca7..0f55c5a1d758cfeb149dafa7bc2af59a7acf826d 100644 (file)
@@ -145,9 +145,21 @@ public:
     const Capabilities &capabilities() const;
     void setCapabilities(const QVariantMap &caps);
 
-    /** Access the server version */
+    /** Access the server version
+     *
+     * For servers >= 10.0.0, this can be the empty string until capabilities
+     * have been received.
+     */
     QString serverVersion() const;
+
+    /** Server version for easy comparison.
+     *
+     * Example: serverVersionInt() >= makeServerVersion(11, 2, 3)
+     *
+     * Will be 0 if the version is not available yet.
+     */
     int serverVersionInt() const;
+
     static int makeServerVersion(int majorVersion, int minorVersion, int patchVersion);
     void setServerVersion(const QString &version);
 
index ec63685aa4cf38560e8e7a4537d04ba22f11328e..76571f186fc9fc56285fc826aa4c61743cc2f221 100644 (file)
@@ -114,26 +114,21 @@ void ConnectionValidator::slotCheckServerAndAuth()
 
 void ConnectionValidator::slotStatusFound(const QUrl&url, const QVariantMap &info)
 {
+    // Newer servers don't disclose any version in status.php anymore
+    // https://github.com/owncloud/core/pull/27473/files
+    // so this string can be empty.
+    QString serverVersion = CheckServerJob::version(info);
+
     // status.php was found.
     qDebug() << "** Application: ownCloud found: "
              << url << " with version "
              << CheckServerJob::versionString(info)
-             << "(" << CheckServerJob::version(info) << ")";
-
-    QString version = CheckServerJob::version(info);
-    _account->setServerVersion(version);
+             << "(" << serverVersion << ")";
 
-    // We cannot deal with servers < 5.0.0
-    if (version.contains('.') && version.split('.')[0].toInt() < 5) {
-        _errors.append( tr("The configured server for this client is too old") );
-        _errors.append( tr("Please update to the latest server and restart the client.") );
-        reportResult( ServerVersionMismatch );
+    if (!serverVersion.isEmpty() && !setAndCheckServerVersion(serverVersion)) {
         return;
     }
 
-    // We attempt to work with servers >= 5.0.0 but warn users.
-    // Check usages of Account::serverVersionUnsupported() for details.
-
     // now check the authentication
     if (_account->credentials()->ready())
         QTimer::singleShot( 0, this, SLOT( checkAuthentication() ));
@@ -235,6 +230,13 @@ void ConnectionValidator::slotCapabilitiesRecieved(const QVariantMap &json)
     auto caps = json.value("ocs").toMap().value("data").toMap().value("capabilities");
     qDebug() << "Server capabilities" << caps;
     _account->setCapabilities(caps.toMap());
+
+    // New servers also report the version in the capabilities
+    QString serverVersion = caps.toMap()["core"].toMap()["status"].toMap()["version"].toString();
+    if (!serverVersion.isEmpty() && !setAndCheckServerVersion(serverVersion)) {
+        return;
+    }
+
     fetchUser();
 }
 
@@ -247,6 +249,26 @@ void ConnectionValidator::fetchUser()
     job->start();
 }
 
+bool ConnectionValidator::setAndCheckServerVersion(const QString& version)
+{
+    qDebug() << _account->url() << "has server version" << version;
+    _account->setServerVersion(version);
+
+    // We cannot deal with servers < 5.0.0
+    if (_account->serverVersionInt()
+            && _account->serverVersionInt() < Account::makeServerVersion(5, 0, 0)) {
+        _errors.append( tr("The configured server for this client is too old") );
+        _errors.append( tr("Please update to the latest server and restart the client.") );
+        reportResult( ServerVersionMismatch );
+        return false;
+    }
+
+    // We attempt to work with servers >= 5.0.0 but warn users.
+    // Check usages of Account::serverVersionUnsupported() for details.
+
+    return true;
+}
+
 void ConnectionValidator::slotUserFetched(const QVariantMap &json)
 {
     QString user = json.value("ocs").toMap().value("data").toMap().value("id").toString();
index 13e1435a5fe6885d564488412d2754762726a2ef..f740b2abd197b1e4d39b34d20b1f19ffcb51a4e7 100644 (file)
@@ -125,6 +125,12 @@ private:
     void checkServerCapabilities();
     void fetchUser();
 
+    /** Sets the account's server version
+     *
+     * Returns false and reports ServerVersionMismatch for very old servers.
+     */
+    bool setAndCheckServerVersion(const QString& version);
+
     QStringList _errors;
     AccountPtr   _account;
     bool _isCheckingServerAndAuth;
index b12c65a8e161e3ebc539be8a17b76d3069e6b304..3bc494f399c1a0b8e5e02571799f9aa297a01bf1 100644 (file)
@@ -474,10 +474,7 @@ bool CheckServerJob::finished()
         }
 
         qDebug() << "status.php returns: " << status << " " << reply()->error() << " Reply: " << reply();
-        if( status.contains("installed")
-                && status.contains("version")
-                && status.contains("versionstring") ) {
-
+        if( status.contains("installed") ) {
             emit instanceFound(reply()->url(), status);
         } else {
             qDebug() << "No proper answer on " << reply()->url();