diff --git a/.drone.yml b/.drone.yml index 39db790270..61368bf80d 100644 --- a/.drone.yml +++ b/.drone.yml @@ -111,6 +111,8 @@ services: - su www-data -c "php /var/www/html/occ app:enable -f testing" - su www-data -c "git clone --depth 1 https://github.com/nextcloud/files_downloadlimit.git /var/www/html/apps/files_downloadlimit/" - su www-data -c "php /var/www/html/occ app:enable -f files_downloadlimit" + - su www-data -c "git clone --depth 1 -b master https://github.com/nextcloud/recommendations.git /var/www/html/apps/recommendations/" + - su www-data -c "php /var/www/html/occ app:enable -f recommendations" - /usr/local/bin/run.sh trigger: @@ -228,6 +230,8 @@ services: - su www-data -c "php /var/www/html/occ app:enable -f testing" - su www-data -c "git clone --depth 1 -b $SERVER_VERSION https://github.com/nextcloud/files_downloadlimit.git /var/www/html/apps/files_downloadlimit/" - su www-data -c "php /var/www/html/occ app:enable -f files_downloadlimit" + - su www-data -c "git clone --depth 1 -b $SERVER_VERSION https://github.com/nextcloud/recommendations.git /var/www/html/apps/recommendations/" + - su www-data -c "php /var/www/html/occ app:enable recommendations" - /usr/local/bin/run.sh trigger: @@ -239,6 +243,6 @@ trigger: - pull_request --- kind: signature -hmac: fe00fcbb3bf41f6aa84193e380345c3b009ef933d295dda86ea3c959a8373381 +hmac: f9e2219ba5004d6abb6eb04ede0dedf0b9d5f20d8769228c1e48a09451a54b06 ... diff --git a/library/src/androidTest/java/com/nextcloud/android/lib/resources/recommendations/GetRecommendationsRemoteOperationIT.kt b/library/src/androidTest/java/com/nextcloud/android/lib/resources/recommendations/GetRecommendationsRemoteOperationIT.kt new file mode 100644 index 0000000000..ac2d4d343e --- /dev/null +++ b/library/src/androidTest/java/com/nextcloud/android/lib/resources/recommendations/GetRecommendationsRemoteOperationIT.kt @@ -0,0 +1,27 @@ +/* + * Nextcloud Android Library + * + * SPDX-FileCopyrightText: 2024 Nextcloud GmbH and Nextcloud contributors + * SPDX-FileCopyrightText: 2024 Tobias Kaminsky + * SPDX-License-Identifier: MIT + */ +package com.nextcloud.android.lib.resources.recommendations + +import com.owncloud.android.AbstractIT +import com.owncloud.android.lib.resources.files.CreateFolderRemoteOperation +import com.owncloud.android.lib.resources.status.NextcloudVersion +import org.junit.Assert.assertTrue +import org.junit.Test + +class GetRecommendationsRemoteOperationIT : AbstractIT() { + @Test + fun getRecommendations() { + testOnlyOnServer(NextcloudVersion.nextcloud_31) + assertTrue(CreateFolderRemoteOperation("/test/", true).execute(client).isSuccess) + + val result = GetRecommendationsRemoteOperation().execute(nextcloudClient).resultData + + assertTrue(result.enabled) + assertTrue(result.recommendations.isNotEmpty()) + } +} diff --git a/library/src/androidTest/java/com/owncloud/android/GetCapabilitiesRemoteOperationIT.java b/library/src/androidTest/java/com/owncloud/android/GetCapabilitiesRemoteOperationIT.java index 5445234bee..a04d200278 100644 --- a/library/src/androidTest/java/com/owncloud/android/GetCapabilitiesRemoteOperationIT.java +++ b/library/src/androidTest/java/com/owncloud/android/GetCapabilitiesRemoteOperationIT.java @@ -9,6 +9,13 @@ */ package com.owncloud.android; +import static org.junit.Assert.assertEquals; +import static org.junit.Assert.assertFalse; +import static org.junit.Assert.assertNotNull; +import static org.junit.Assert.assertNotSame; +import static org.junit.Assert.assertSame; +import static org.junit.Assert.assertTrue; + import com.owncloud.android.lib.common.operations.RemoteOperationResult; import com.owncloud.android.lib.resources.status.CapabilityBooleanType; import com.owncloud.android.lib.resources.status.E2EVersion; @@ -19,13 +26,6 @@ import org.junit.Test; -import static org.junit.Assert.assertEquals; -import static org.junit.Assert.assertFalse; -import static org.junit.Assert.assertNotNull; -import static org.junit.Assert.assertNotSame; -import static org.junit.Assert.assertSame; -import static org.junit.Assert.assertTrue; - /** * Class to test GetRemoteCapabilitiesOperation */ @@ -154,5 +154,10 @@ private void checkCapability(OCCapability capability, String userId) { // e2e assertNotSame(capability.getEndToEndEncryptionApiVersion(), E2EVersion.UNKNOWN); + + // recommendations + if (capability.getVersion().isNewerOrEqual(NextcloudVersion.nextcloud_31)) { + assertTrue(capability.getRecommendations().isTrue()); + } } } diff --git a/library/src/main/java/com/nextcloud/android/lib/resources/recommendations/GetRecommendationsRemoteOperation.kt b/library/src/main/java/com/nextcloud/android/lib/resources/recommendations/GetRecommendationsRemoteOperation.kt new file mode 100644 index 0000000000..09bd0267d7 --- /dev/null +++ b/library/src/main/java/com/nextcloud/android/lib/resources/recommendations/GetRecommendationsRemoteOperation.kt @@ -0,0 +1,67 @@ +/* + * Nextcloud Android Library + * + * SPDX-FileCopyrightText: 2024 Nextcloud GmbH and Nextcloud contributors + * SPDX-FileCopyrightText: 2024 Tobias Kaminsky + * SPDX-License-Identifier: MIT + */ +package com.nextcloud.android.lib.resources.recommendations + +import com.google.gson.reflect.TypeToken +import com.nextcloud.common.NextcloudClient +import com.nextcloud.operations.GetMethod +import com.owncloud.android.lib.common.operations.RemoteOperationResult +import com.owncloud.android.lib.common.utils.Log_OC +import com.owncloud.android.lib.ocs.ServerResponse +import com.owncloud.android.lib.resources.OCSRemoteOperation +import org.apache.commons.httpclient.HttpStatus + +/** + * Get recommendation of an user + */ +class GetRecommendationsRemoteOperation : OCSRemoteOperation() { + @Suppress("TooGenericExceptionCaught") + override fun run(client: NextcloudClient): RemoteOperationResult { + var result: RemoteOperationResult + var getMethod: GetMethod? = null + try { + getMethod = + GetMethod( + client.baseUri.toString() + ENDPOINT + JSON_FORMAT, + true + ) + val status = client.execute(getMethod) + if (status == HttpStatus.SC_OK) { + val map = + getServerResponse( + getMethod, + object : TypeToken>() {} + )?.ocs?.data + + if (map != null) { + result = RemoteOperationResult(true, getMethod) + result.setResultData(map) + } else { + result = RemoteOperationResult(false, getMethod) + } + } else { + result = RemoteOperationResult(false, getMethod) + } + } catch (e: Exception) { + result = RemoteOperationResult(e) + Log_OC.e( + TAG, + "Get recommendations failed: " + result.logMessage, + result.exception + ) + } finally { + getMethod?.releaseConnection() + } + return result + } + + companion object { + private val TAG = GetRecommendationsRemoteOperation::class.java.simpleName + private const val ENDPOINT = "/ocs/v2.php/apps/recommendations/api/v1/recommendations" + } +} diff --git a/library/src/main/java/com/nextcloud/android/lib/resources/recommendations/Recommendation.kt b/library/src/main/java/com/nextcloud/android/lib/resources/recommendations/Recommendation.kt new file mode 100644 index 0000000000..70eca33764 --- /dev/null +++ b/library/src/main/java/com/nextcloud/android/lib/resources/recommendations/Recommendation.kt @@ -0,0 +1,20 @@ +/* + * Nextcloud Android Library + * + * SPDX-FileCopyrightText: 2024 Nextcloud GmbH and Nextcloud contributors + * SPDX-FileCopyrightText: 2024 Tobias Kaminsky + * SPDX-License-Identifier: MIT + */ + +package com.nextcloud.android.lib.resources.recommendations + +data class Recommendation( + val id: Long, + val timestamp: Long, + val name: String, + val directory: String, + val extension: String, + val mimeType: String, + val hasPreview: Boolean, + val reason: String +) diff --git a/library/src/main/java/com/nextcloud/android/lib/resources/recommendations/RecommendationResponse.kt b/library/src/main/java/com/nextcloud/android/lib/resources/recommendations/RecommendationResponse.kt new file mode 100644 index 0000000000..30e1400f5c --- /dev/null +++ b/library/src/main/java/com/nextcloud/android/lib/resources/recommendations/RecommendationResponse.kt @@ -0,0 +1,14 @@ +/* + * Nextcloud Android Library + * + * SPDX-FileCopyrightText: 2024 Nextcloud GmbH and Nextcloud contributors + * SPDX-FileCopyrightText: 2024 Tobias Kaminsky + * SPDX-License-Identifier: MIT + */ + +package com.nextcloud.android.lib.resources.recommendations + +data class RecommendationResponse( + val enabled: Boolean, + val recommendations: ArrayList +) diff --git a/library/src/main/java/com/owncloud/android/lib/resources/status/GetCapabilitiesRemoteOperation.java b/library/src/main/java/com/owncloud/android/lib/resources/status/GetCapabilitiesRemoteOperation.java index 5a5c3f7068..5e1d86a845 100644 --- a/library/src/main/java/com/owncloud/android/lib/resources/status/GetCapabilitiesRemoteOperation.java +++ b/library/src/main/java/com/owncloud/android/lib/resources/status/GetCapabilitiesRemoteOperation.java @@ -160,6 +160,9 @@ public class GetCapabilitiesRemoteOperation extends RemoteOperation { private static final String NODE_SECURITY_GUARD = "security_guard"; private static final String NODE_DIAGNOSTICS = "diagnostics"; + //recommendations + private static final String NODE_RECOMMENDATIONS = "recommendations"; + // needed for checking compatible filenames private static final String FORBIDDEN_FILENAME_CHARACTERS = "forbidden_filename_characters"; private static final String FORBIDDEN_FILENAMES = "forbidden_filenames"; @@ -754,6 +757,19 @@ private OCCapability parseResponse(String response) throws JSONException { capability.setFilesDownloadLimitDefault(defaultDownloadLimit); } } + + // recommendations + if (respCapabilities.has(NODE_RECOMMENDATIONS)) { + JSONObject recommendationsCapability = respCapabilities.getJSONObject(NODE_RECOMMENDATIONS); + + if (recommendationsCapability.getBoolean(PROPERTY_ENABLED)) { + capability.setRecommendations(CapabilityBooleanType.TRUE); + } else { + capability.setRecommendations(CapabilityBooleanType.FALSE); + } + } else { + capability.setRecommendations(CapabilityBooleanType.FALSE); + } } Log_OC.d(TAG, "*** Get Capabilities completed "); diff --git a/library/src/main/java/com/owncloud/android/lib/resources/status/NextcloudVersion.kt b/library/src/main/java/com/owncloud/android/lib/resources/status/NextcloudVersion.kt index 5fc1d25cff..50ffa3608c 100644 --- a/library/src/main/java/com/owncloud/android/lib/resources/status/NextcloudVersion.kt +++ b/library/src/main/java/com/owncloud/android/lib/resources/status/NextcloudVersion.kt @@ -38,6 +38,9 @@ class NextcloudVersion : OwnCloudVersion { @JvmField val nextcloud_30 = NextcloudVersion(0x1E000000) // 30.0 + + @JvmField + val nextcloud_31 = NextcloudVersion(0x1F000000) // 31.0 } constructor(string: String) : super(string) diff --git a/library/src/main/java/com/owncloud/android/lib/resources/status/OCCapability.kt b/library/src/main/java/com/owncloud/android/lib/resources/status/OCCapability.kt index 0ba53fe14d..b3873d686f 100644 --- a/library/src/main/java/com/owncloud/android/lib/resources/status/OCCapability.kt +++ b/library/src/main/java/com/owncloud/android/lib/resources/status/OCCapability.kt @@ -104,6 +104,9 @@ class OCCapability { // Security guard var securityGuard = CapabilityBooleanType.UNKNOWN + // Recommendations + var recommendations = CapabilityBooleanType.UNKNOWN + // needed for checking compatible filenames var forbiddenFilenameCharactersJson: String? = null var forbiddenFilenamesJson: String? = null