From b10e74afec37d0968e0dd69c7c9194ca84686ebf Mon Sep 17 00:00:00 2001 From: agarcia Date: Mon, 20 Apr 2020 12:12:26 +0200 Subject: [PATCH] Use moshi to parse capabilities --- .../resources/response/CapabilityResponse.kt | 102 ++++++++++-------- .../{ => response}/CommonOcsResponse.kt | 2 +- .../lib/resources/response/CommonResponse.kt | 45 -------- .../{users => response}/UserInfoResponse.kt | 10 +- .../status/GetRemoteCapabilitiesOperation.kt | 94 ++++------------ .../users/GetRemoteUserInfoOperation.kt | 6 +- 6 files changed, 89 insertions(+), 170 deletions(-) rename owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/{ => response}/CommonOcsResponse.kt (97%) delete mode 100644 owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CommonResponse.kt rename owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/{users => response}/UserInfoResponse.kt (90%) diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CapabilityResponse.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CapabilityResponse.kt index bfa03726..90ed459d 100644 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CapabilityResponse.kt +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CapabilityResponse.kt @@ -24,23 +24,61 @@ */ package com.owncloud.android.lib.resources.response +import com.owncloud.android.lib.resources.status.RemoteCapability +import com.owncloud.android.lib.resources.status.RemoteCapability.CapabilityBooleanType import com.squareup.moshi.Json import com.squareup.moshi.JsonClass @JsonClass(generateAdapter = true) data class CapabilityResponse( - @Json(name = NODE_SERVER_VERSION) + @Json(name = "version") val serverVersion: ServerVersion, val capabilities: Capabilities -) +) { + fun toRemoteCapability(): RemoteCapability = RemoteCapability( + versionMayor = serverVersion.major, + versionMinor = serverVersion.minor, + versionMicro = serverVersion.micro, + versionString = serverVersion.string, + versionEdition = serverVersion.edition, + corePollinterval = capabilities.coreCapabilities.pollinterval, + filesSharingApiEnabled = CapabilityBooleanType.fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingApiEnabled), + filesSharingResharing = CapabilityBooleanType.fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingReSharing), + filesSharingPublicEnabled = CapabilityBooleanType.fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.enabled), + filesSharingPublicUpload = CapabilityBooleanType.fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicUpload), + filesSharingPublicSupportsUploadOnly = CapabilityBooleanType.fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicUploadOnly), + filesSharingPublicMultiple = CapabilityBooleanType.fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicMultiple), + filesSharingPublicPasswordEnforced = CapabilityBooleanType.fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicPassword.enforced), + filesSharingPublicPasswordEnforcedReadOnly = CapabilityBooleanType.fromBooleanValue( + capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicPassword.enforcedFor.enforcedReadOnly + ), + filesSharingPublicPasswordEnforcedReadWrite = CapabilityBooleanType.fromBooleanValue( + capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicPassword.enforcedFor.enforcedReadWrite + ), + filesSharingPublicPasswordEnforcedUploadOnly = CapabilityBooleanType.fromBooleanValue( + capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicPassword.enforcedFor.enforcedUploadOnly + ), + filesSharingPublicExpireDateEnabled = CapabilityBooleanType.fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicExpireDate.enabled), + filesSharingPublicExpireDateDays = capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicExpireDate.days + ?: 0, + filesSharingPublicExpireDateEnforced = CapabilityBooleanType.fromBooleanValue( + capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicExpireDate.enforced ?: false + ), + filesBigFileChunking = CapabilityBooleanType.fromBooleanValue(capabilities.filesCapabilities.bigfilechunking), + filesUndelete = CapabilityBooleanType.fromBooleanValue(capabilities.filesCapabilities.undelete), + filesVersioning = CapabilityBooleanType.fromBooleanValue(capabilities.filesCapabilities.versioning), + filesSharingFederationIncoming = CapabilityBooleanType.fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingFederation.incoming), + filesSharingFederationOutgoing = CapabilityBooleanType.fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingFederation.outgoing) + ) +} @JsonClass(generateAdapter = true) data class Capabilities( - @Json(name = NODE_CORE) + @Json(name = "core") val coreCapabilities: CoreCapabilities, - @Json(name = NODE_FILES_SHARING) + @Json(name = "files_sharing") val fileSharingCapabilities: FileSharingCapabilities, - @Json(name = NODE_FILES) + @Json(name = "files") val filesCapabilities: FilesCapabilities ) @@ -51,47 +89,45 @@ data class CoreCapabilities( @JsonClass(generateAdapter = true) data class FileSharingCapabilities( - @Json(name = PROPERTY_FILES_SHARING_API_ENABLED) + @Json(name = "api_enabled") val fileSharingApiEnabled: Boolean, - @Json(name = PROPERTY_FILES_SHARING_SEARCH_MIN_LENGTH) - val fileSharingSearchMinLength: Int, - @Json(name = NODE_FILES_SHARING_PUBLIC) + @Json(name = "public") val fileSharingPublic: FileSharingPublic, - @Json(name = PROPERTY_FILES_SHARING_RESHARING) + @Json(name = "resharing") val fileSharingReSharing: Boolean, - @Json(name = NODE_FEDERATION) + @Json(name = "federation") val fileSharingFederation: FileSharingFederation ) @JsonClass(generateAdapter = true) data class FileSharingPublic( val enabled: Boolean, - @Json(name = PROPERTY_FILES_SHARING_PUBLIC_UPLOAD) + @Json(name = "upload") val fileSharingPublicUpload: Boolean, - @Json(name = PROPERTY_FILES_SHARING_PUBLIC_UPLOAD_ONLY) + @Json(name = "supports_upload_only") val fileSharingPublicUploadOnly: Boolean, - @Json(name = PROPERTY_FILES_SHARING_PUBLIC_MULTIPLE) + @Json(name = "multiple") val fileSharingPublicMultiple: Boolean, - @Json(name = NODE_PASSWORD) + @Json(name = "password") val fileSharingPublicPassword: FileSharingPublicPassword, - @Json(name = NODE_EXPIRE_DATE) + @Json(name = "expire_date") val fileSharingPublicExpireDate: FileSharingPublicExpireDate ) @JsonClass(generateAdapter = true) data class FileSharingPublicPassword( val enforced: Boolean, - @Json(name = NODE_FILES_SHARING_PUBLIC_PASSWORD_ENFORCED) + @Json(name = "enforced_for") val enforcedFor: FileSharingPublicPasswordEnforced ) @JsonClass(generateAdapter = true) data class FileSharingPublicPasswordEnforced( - @Json(name = PROPERTY_FILES_SHARING_PUBLIC_PASSWORD_ENFORCED_READ_ONLY) + @Json(name = "read_only") val enforcedReadOnly: Boolean, - @Json(name = PROPERTY_FILES_SHARING_PUBLIC_PASSWORD_ENFORCED_READ_WRITE) + @Json(name = "read_write") val enforcedReadWrite: Boolean, - @Json(name = PROPERTY_FILES_SHARING_PUBLIC_PASSWORD_ENFORCED_UPLOAD_ONLY) + @Json(name = "upload_only") val enforcedUploadOnly: Boolean ) @@ -123,29 +159,3 @@ data class ServerVersion( var string: String = "", var edition: String = "" ) - -private const val NODE_SERVER_VERSION = "version" - -private const val NODE_CORE = "core" - -private const val NODE_FILES_SHARING = "files_sharing" -private const val PROPERTY_FILES_SHARING_API_ENABLED = "api_enabled" -private const val PROPERTY_FILES_SHARING_SEARCH_MIN_LENGTH = "search_min_length" -private const val PROPERTY_FILES_SHARING_RESHARING = "resharing" - -private const val NODE_FILES_SHARING_PUBLIC = "public" -private const val PROPERTY_FILES_SHARING_PUBLIC_UPLOAD = "upload" -private const val PROPERTY_FILES_SHARING_PUBLIC_UPLOAD_ONLY = "supports_upload_only" -private const val PROPERTY_FILES_SHARING_PUBLIC_MULTIPLE = "multiple" - -private const val NODE_FEDERATION = "federation" - -private const val NODE_PASSWORD = "password" -private const val NODE_FILES_SHARING_PUBLIC_PASSWORD_ENFORCED = "enforced_for" -private const val PROPERTY_FILES_SHARING_PUBLIC_PASSWORD_ENFORCED_READ_ONLY = "read_only" -private const val PROPERTY_FILES_SHARING_PUBLIC_PASSWORD_ENFORCED_READ_WRITE = "read_write" -private const val PROPERTY_FILES_SHARING_PUBLIC_PASSWORD_ENFORCED_UPLOAD_ONLY = "upload_only" - -private const val NODE_EXPIRE_DATE = "expire_date" - -private const val NODE_FILES = "files" diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/CommonOcsResponse.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CommonOcsResponse.kt similarity index 97% rename from owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/CommonOcsResponse.kt rename to owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CommonOcsResponse.kt index 2cfbe2ed..d8402eb9 100644 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/CommonOcsResponse.kt +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CommonOcsResponse.kt @@ -21,7 +21,7 @@ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN * THE SOFTWARE. */ -package com.owncloud.android.lib.resources +package com.owncloud.android.lib.resources.response import com.squareup.moshi.JsonClass diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CommonResponse.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CommonResponse.kt deleted file mode 100644 index e0d8bbf6..00000000 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/CommonResponse.kt +++ /dev/null @@ -1,45 +0,0 @@ -/* ownCloud Android Library is available under MIT license - * - * @author Abel GarcĂ­a de Prada - * 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.response - -import com.squareup.moshi.JsonClass - -@JsonClass(generateAdapter = true) -data class CommonResponse( - val ocs: OCSResponse -) - -@JsonClass(generateAdapter = true) -data class OCSResponse( - val meta: MetaData, - val data: T -) - -@JsonClass(generateAdapter = true) -data class MetaData( - val status: String, - val statuscode: Int, - val message: String? -) diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/users/UserInfoResponse.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/UserInfoResponse.kt similarity index 90% rename from owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/users/UserInfoResponse.kt rename to owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/UserInfoResponse.kt index d0fdcf82..1ff3b94e 100644 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/users/UserInfoResponse.kt +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/response/UserInfoResponse.kt @@ -21,8 +21,9 @@ * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN * THE SOFTWARE. */ -package com.owncloud.android.lib.resources.users +package com.owncloud.android.lib.resources.response +import com.owncloud.android.lib.resources.users.RemoteUserInfo import com.squareup.moshi.Json import com.squareup.moshi.JsonClass @@ -32,11 +33,10 @@ data class UserInfoResponse( @Json(name = "display-name") val displayName: String, val email: String? -) - -fun UserInfoResponse.toRemoteUserInfo() = - RemoteUserInfo( +) { + fun toRemoteUserInfo() = RemoteUserInfo( id = id, displayName = displayName, email = email ) +} diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/GetRemoteCapabilitiesOperation.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/GetRemoteCapabilitiesOperation.kt index 41fd7ab9..d3af0df2 100644 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/GetRemoteCapabilitiesOperation.kt +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/status/GetRemoteCapabilitiesOperation.kt @@ -35,12 +35,10 @@ 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.OK import com.owncloud.android.lib.resources.response.CapabilityResponse -import com.owncloud.android.lib.resources.response.CommonResponse -import com.owncloud.android.lib.resources.status.RemoteCapability.CapabilityBooleanType.Companion.fromBooleanValue +import com.owncloud.android.lib.resources.response.CommonOcsResponse import com.squareup.moshi.JsonAdapter import com.squareup.moshi.Moshi import com.squareup.moshi.Types -import com.squareup.moshi.kotlin.reflect.KotlinJsonAdapterFactory import timber.log.Timber import java.lang.reflect.Type import java.net.URL @@ -58,49 +56,33 @@ class GetRemoteCapabilitiesOperation : RemoteOperation() { var result: RemoteOperationResult try { - val requestUri = client.baseUri - val uriBuilder = requestUri.buildUpon() - uriBuilder.appendEncodedPath(OCS_ROUTE) // avoid starting "/" in this method - uriBuilder.appendQueryParameter(PARAM_FORMAT, VALUE_FORMAT) - - val getMethod = GetMethod(URL(uriBuilder.build().toString())) - - getMethod.addRequestHeader(OCS_API_HEADER, OCS_API_HEADER_VALUE) - + val uriBuilder = client.baseUri.buildUpon().run { + appendEncodedPath(OCS_ROUTE) // avoid starting "/" in this method + appendQueryParameter(PARAM_FORMAT, VALUE_FORMAT) + } + val getMethod = GetMethod(URL(uriBuilder.build().toString())).apply { + addRequestHeader(OCS_API_HEADER, OCS_API_HEADER_VALUE) + } val status = client.executeHttpMethod(getMethod) val response = getMethod.responseBodyAsString - if (status != HttpConstants.HTTP_OK) { + if (status == HttpConstants.HTTP_OK) { + Timber.d("Successful response $response") + + // Parse the response + val moshi: Moshi = Moshi.Builder().build() + val type: Type = Types.newParameterizedType(CommonOcsResponse::class.java, CapabilityResponse::class.java) + val adapter: JsonAdapter> = moshi.adapter(type) + val commonResponse: CommonOcsResponse? = adapter.fromJson(response) + + result = RemoteOperationResult(OK) + result.data = commonResponse?.ocs?.data?.toRemoteCapability() + + Timber.d("*** Get Capabilities completed and parsed to ${result.data}") + } else { result = RemoteOperationResult(getMethod) Timber.e("Failed response while getting capabilities from the server status code: $status; response message: $response") - return result - } - - Timber.d("Successful response: $response") - - // Parse the response - val moshi: Moshi = Moshi.Builder().add(KotlinJsonAdapterFactory()).build() - val type: Type = Types.newParameterizedType(CommonResponse::class.java, CapabilityResponse::class.java) - val adapter: JsonAdapter> = moshi.adapter(type) - val commonResponse: CommonResponse? = adapter.fromJson(response) - - // Read MetaData - val statusMessage = commonResponse?.ocs?.meta?.status - val statusCode = commonResponse?.ocs?.meta?.statuscode - val message = commonResponse?.ocs?.meta?.message - - if (statusMessage.equals(PROPERTY_STATUS_OK, ignoreCase = true)) { - val remoteCapability = commonResponse?.ocs?.data?.let { mapToModel(it) } ?: RemoteCapability() - // Result - result = RemoteOperationResult(OK) - result.data = remoteCapability - - Timber.d("*** Get Capabilities completed and parsed to: $remoteCapability") - } else { - result = RemoteOperationResult(statusCode!!, message, null) - Timber.e("Failed response while getting capabilities from the server ") - Timber.e("*** statusCode: $status; status: $statusMessage; message: $message") } } catch (e: Exception) { @@ -111,36 +93,6 @@ class GetRemoteCapabilitiesOperation : RemoteOperation() { return result } - private fun mapToModel(capabilityResponse: CapabilityResponse): RemoteCapability = - with(capabilityResponse) { - RemoteCapability( - versionMayor = serverVersion.major, - versionMinor = serverVersion.minor, - versionMicro = serverVersion.micro, - versionString = serverVersion.string, - versionEdition = serverVersion.edition, - corePollinterval = capabilities.coreCapabilities.pollinterval, - filesSharingApiEnabled = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingApiEnabled), - filesSharingResharing = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingReSharing), - filesSharingPublicEnabled = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.enabled), - filesSharingPublicUpload = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicUpload), - filesSharingPublicSupportsUploadOnly = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicUploadOnly), - filesSharingPublicMultiple = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicMultiple), - filesSharingPublicPasswordEnforced = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicPassword.enforced), - filesSharingPublicPasswordEnforcedReadOnly = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicPassword.enforcedFor.enforcedReadOnly), - filesSharingPublicPasswordEnforcedReadWrite = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicPassword.enforcedFor.enforcedReadWrite), - filesSharingPublicPasswordEnforcedUploadOnly = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicPassword.enforcedFor.enforcedUploadOnly), - filesSharingPublicExpireDateEnabled = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicExpireDate.enabled), - filesSharingPublicExpireDateDays = capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicExpireDate.days ?: 0, - filesSharingPublicExpireDateEnforced = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingPublic.fileSharingPublicExpireDate.enforced?:false), - filesBigFileChunking = fromBooleanValue(capabilities.filesCapabilities.bigfilechunking), - filesUndelete = fromBooleanValue(capabilities.filesCapabilities.undelete), - filesVersioning = fromBooleanValue(capabilities.filesCapabilities.versioning), - filesSharingFederationIncoming = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingFederation.incoming), - filesSharingFederationOutgoing = fromBooleanValue(capabilities.fileSharingCapabilities.fileSharingFederation.outgoing) - ) - } - companion object { // OCS Routes @@ -151,7 +103,5 @@ class GetRemoteCapabilitiesOperation : RemoteOperation() { // Arguments - constant values private const val VALUE_FORMAT = "json" - - private const val PROPERTY_STATUS_OK = "ok" } } diff --git a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/users/GetRemoteUserInfoOperation.kt b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/users/GetRemoteUserInfoOperation.kt index 54aeb32f..d370b449 100644 --- a/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/users/GetRemoteUserInfoOperation.kt +++ b/owncloudComLibrary/src/main/java/com/owncloud/android/lib/resources/users/GetRemoteUserInfoOperation.kt @@ -29,7 +29,8 @@ import com.owncloud.android.lib.common.http.methods.nonwebdav.GetMethod 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.CommonOcsResponse +import com.owncloud.android.lib.resources.response.CommonOcsResponse +import com.owncloud.android.lib.resources.response.UserInfoResponse import com.squareup.moshi.JsonAdapter import com.squareup.moshi.Moshi import com.squareup.moshi.Types @@ -63,6 +64,9 @@ class GetRemoteUserInfoOperation : RemoteOperation() { result = RemoteOperationResult(ResultCode.OK) result.data = commonResponse?.ocs?.data?.toRemoteUserInfo() + + Timber.d("*** Get User Info completed and parsed to ${result.data}") + } else { result = RemoteOperationResult(getMethod) Timber.e("Failed response while getting user information status code: $status, response: $response")