diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/common/OwnCloudClientFactory.java b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/common/OwnCloudClientFactory.java index f5c64bfa..948e8a07 100644 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/common/OwnCloudClientFactory.java +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/common/OwnCloudClientFactory.java @@ -27,6 +27,7 @@ package com.owncloud.android.lib.common; import android.content.Context; import android.net.Uri; +import com.owncloud.android.lib.common.http.HttpClient; import com.owncloud.android.lib.resources.status.GetRemoteStatusOperation; public class OwnCloudClientFactory { @@ -44,13 +45,13 @@ public class OwnCloudClientFactory { client.setFollowRedirects(followRedirects); - client.setContext(context); - retriveCookisFromMiddleware(client); + HttpClient.setContext(context); + retrieveCookiesFromMiddleware(client); return client; } - public static void retriveCookisFromMiddleware(OwnCloudClient client) { + private static void retrieveCookiesFromMiddleware(OwnCloudClient client) { final GetRemoteStatusOperation statusOperation = new GetRemoteStatusOperation(); statusOperation.run(client); } diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/GetRemoteStatusOperation.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/GetRemoteStatusOperation.kt index 10d543c0..eeb2aadf 100644 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/GetRemoteStatusOperation.kt +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/GetRemoteStatusOperation.kt @@ -29,7 +29,6 @@ import com.owncloud.android.lib.common.operations.RemoteOperation import com.owncloud.android.lib.common.operations.RemoteOperationResult import com.owncloud.android.lib.common.operations.RemoteOperationResult.ResultCode import com.owncloud.android.lib.resources.status.HttpScheme.HTTPS_PREFIX -import com.owncloud.android.lib.resources.status.HttpScheme.HTTPS_SCHEME import com.owncloud.android.lib.resources.status.HttpScheme.HTTP_PREFIX import com.owncloud.android.lib.resources.status.HttpScheme.HTTP_SCHEME import org.json.JSONException @@ -43,15 +42,13 @@ import timber.log.Timber * @author David González Verdugo * @author Abel García de Prada */ -class GetRemoteStatusOperation : RemoteOperation() { +class GetRemoteStatusOperation : RemoteOperation() { - public override fun run(client: OwnCloudClient): RemoteOperationResult { + public override fun run(client: OwnCloudClient): RemoteOperationResult { client.baseUri = buildFullHttpsUrl(client.baseUri) var result = tryToConnect(client) - if (!(result.code == ResultCode.OK || result.code == ResultCode.OK_SSL) - && !result.isSslRecoverableException - ) { + if (!(result.code == ResultCode.OK || result.code == ResultCode.OK_SSL) && !result.isSslRecoverableException) { Timber.d("Establishing secure connection failed, trying non secure connection") client.baseUri = client.baseUri.buildUpon().scheme(HTTP_SCHEME).build() result = tryToConnect(client) @@ -60,7 +57,7 @@ class GetRemoteStatusOperation : RemoteOperation() { return result } - private fun tryToConnect(client: OwnCloudClient): RemoteOperationResult { + private fun tryToConnect(client: OwnCloudClient): RemoteOperationResult { val baseUrl = client.baseUri.toString() client.setFollowRedirects(false) return try { diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/RemoteServerInfo.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/RemoteServerInfo.kt new file mode 100644 index 00000000..5938368d --- /dev/null +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/RemoteServerInfo.kt @@ -0,0 +1,30 @@ +/* ownCloud Android Library is available under MIT license +* Copyright (C) 2020 ownCloud GmbH. +* +* Permission is hereby granted, free of charge, to any person obtaining a copy +* of this software and associated documentation files (the "Software"), to deal +* in the Software without restriction, including without limitation the rights +* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +* copies of the Software, and to permit persons to whom the Software is +* furnished to do so, subject to the following conditions: +* +* The above copyright notice and this permission notice shall be included in +* all copies or substantial portions of the Software. +* +* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, +* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF +* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND +* NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS +* BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN +* ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN +* CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +* THE SOFTWARE. +* +*/ +package com.owncloud.android.lib.resources.status + +data class RemoteServerInfo( + val ownCloudVersion: OwnCloudVersion, + val baseUrl: String, + val isSecureConnection: Boolean +) diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/StatusRequester.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/StatusRequester.kt index c19b9bea..842c7d36 100644 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/StatusRequester.kt +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/StatusRequester.kt @@ -28,9 +28,7 @@ import com.owncloud.android.lib.common.OwnCloudClient import com.owncloud.android.lib.common.http.HttpConstants import com.owncloud.android.lib.common.http.methods.nonwebdav.GetMethod import com.owncloud.android.lib.common.operations.RemoteOperationResult - import com.owncloud.android.lib.resources.status.HttpScheme.HTTPS_SCHEME -import com.owncloud.android.lib.resources.status.HttpScheme.HTTP_SCHEME import org.json.JSONObject import java.net.URL import java.util.concurrent.TimeUnit @@ -44,14 +42,21 @@ internal class StatusRequester { * we assume it was a debug setup. */ fun isRedirectedToNonSecureConnection( - redirectedToUnsecureLocationBefore: Boolean, + redirectedToNonSecureLocationBefore: Boolean, baseUrl: String, redirectedUrl: String - ) = redirectedToUnsecureLocationBefore + ) = redirectedToNonSecureLocationBefore || (baseUrl.startsWith(HTTPS_SCHEME) && !redirectedUrl.startsWith(HTTPS_SCHEME)) fun updateLocationWithRedirectPath(oldLocation: String, redirectedLocation: String): String { + /** Redirection with different endpoint. + * When asking for server.com/status.php and redirected to different.one/, we need to ask different.one/status.php + */ + if (redirectedLocation.endsWith('/')) { + return redirectedLocation.trimEnd('/') + OwnCloudClient.STATUS_PATH + } + if (!redirectedLocation.startsWith("/")) return redirectedLocation val oldLocationURL = URL(oldLocation) @@ -68,7 +73,8 @@ internal class StatusRequester { data class RequestResult( val getMethod: GetMethod, val status: Int, - val redirectedToUnsecureLocation: Boolean + val redirectedToUnsecureLocation: Boolean, + val lastLocation: String ) fun requestAndFollowRedirects(baseLocation: String, client: OwnCloudClient): RequestResult { @@ -85,7 +91,7 @@ internal class StatusRequester { else RemoteOperationResult(getMethod) if (result.redirectedLocation.isNullOrEmpty() || result.isSuccess) { - return RequestResult(getMethod, status, redirectedToUnsecureLocation) + return RequestResult(getMethod, status, redirectedToUnsecureLocation, currentLocation) } else { val nextLocation = updateLocationWithRedirectPath(currentLocation, result.redirectedLocation) redirectedToUnsecureLocation = @@ -104,7 +110,7 @@ internal class StatusRequester { fun handleRequestResult( requestResult: RequestResult, baseUrl: String - ): RemoteOperationResult { + ): RemoteOperationResult { if (!requestResult.status.isSuccess()) return RemoteOperationResult(requestResult.getMethod) @@ -115,25 +121,35 @@ internal class StatusRequester { val ocVersion = OwnCloudVersion(respJSON.getString(NODE_VERSION)) // the version object will be returned even if the version is invalid, no error code; // every app will decide how to act if (ocVersion.isVersionValid() == false) - val result = + val result: RemoteOperationResult = if (requestResult.redirectedToUnsecureLocation) { - RemoteOperationResult(RemoteOperationResult.ResultCode.OK_REDIRECT_TO_NON_SECURE_CONNECTION) + RemoteOperationResult(RemoteOperationResult.ResultCode.OK_REDIRECT_TO_NON_SECURE_CONNECTION) } else { - if (baseUrl.startsWith(HTTPS_SCHEME)) RemoteOperationResult( - RemoteOperationResult.ResultCode.OK_SSL - ) + if (baseUrl.startsWith(HTTPS_SCHEME)) RemoteOperationResult(RemoteOperationResult.ResultCode.OK_SSL) else RemoteOperationResult(RemoteOperationResult.ResultCode.OK_NO_SSL) } - result.data = ocVersion + val finalUrl = URL(requestResult.lastLocation) + val finalBaseUrl = URL( + finalUrl.protocol, + finalUrl.host, + finalUrl.port, + finalUrl.file.dropLastWhile { it != '/' }.trimEnd('/') + ) + + result.data = RemoteServerInfo( + ownCloudVersion = ocVersion, + baseUrl = finalBaseUrl.toString(), + isSecureConnection = finalBaseUrl.protocol.startsWith(HTTPS_SCHEME) + ) return result } companion object { /** * Maximum time to wait for a response from the server when the connection is being tested, - * in MILLISECONDs. + * in milliseconds. */ - private const val TRY_CONNECTION_TIMEOUT: Long = 5000 + private const val TRY_CONNECTION_TIMEOUT = 5_000L private const val NODE_INSTALLED = "installed" private const val NODE_VERSION = "version" } diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/services/ServerInfoService.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/services/ServerInfoService.kt index 121f617f..911b2b80 100644 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/services/ServerInfoService.kt +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/services/ServerInfoService.kt @@ -25,10 +25,10 @@ package com.owncloud.android.lib.resources.status.services import com.owncloud.android.lib.common.OwnCloudClient import com.owncloud.android.lib.common.operations.RemoteOperationResult -import com.owncloud.android.lib.resources.status.OwnCloudVersion +import com.owncloud.android.lib.resources.status.RemoteServerInfo interface ServerInfoService { fun checkPathExistence(path: String, isUserLogged: Boolean, client: OwnCloudClient): RemoteOperationResult - fun getRemoteStatus(path: String, client: OwnCloudClient): RemoteOperationResult + fun getRemoteStatus(path: String, client: OwnCloudClient): RemoteOperationResult } diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/services/implementation/OCServerInfoService.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/services/implementation/OCServerInfoService.kt index 65b85479..0dbae093 100644 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/services/implementation/OCServerInfoService.kt +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/services/implementation/OCServerInfoService.kt @@ -23,7 +23,7 @@ import com.owncloud.android.lib.common.OwnCloudClient import com.owncloud.android.lib.common.operations.RemoteOperationResult import com.owncloud.android.lib.resources.files.CheckPathExistenceRemoteOperation import com.owncloud.android.lib.resources.status.GetRemoteStatusOperation -import com.owncloud.android.lib.resources.status.OwnCloudVersion +import com.owncloud.android.lib.resources.status.RemoteServerInfo import com.owncloud.android.lib.resources.status.services.ServerInfoService class OCServerInfoService : ServerInfoService { @@ -41,6 +41,6 @@ class OCServerInfoService : ServerInfoService { override fun getRemoteStatus( path: String, client: OwnCloudClient - ): RemoteOperationResult = + ): RemoteOperationResult = GetRemoteStatusOperation().execute(client) }