diff --git a/CHANGELOG.md b/CHANGELOG.md index 0daed689..f31170b7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,14 @@ # Change Log +## 14.0.0 + +* [BREAKING] Changed `$sequence` type from `Long` to `String` for `Row` and `Document` models +* Added impersonation support: `setImpersonateUserId()`, `setImpersonateUserEmail()`, `setImpersonateUserPhone()` on `Client` +* Added `impersonator` and `impersonatorUserId` optional fields to `User` model +* Updated `Log` model field descriptions to clarify impersonation behavior for `userId`, `userEmail`, `userName` +* Updated `X-Appwrite-Response-Format` header to `1.9.0` +* Updated API version badge to `1.9.0` and compatibility note to server version `1.9.x` in README + ## 13.0.0 * Breaking: Channel factory methods require explicit IDs (no wildcard defaults) diff --git a/README.md b/README.md index 97afbafe..05d1ef38 100644 --- a/README.md +++ b/README.md @@ -2,12 +2,12 @@ ![Maven Central](https://img.shields.io/maven-central/v/io.appwrite/sdk-for-android.svg?color=green&style=flat-square) ![License](https://img.shields.io/github/license/appwrite/sdk-for-android.svg?style=flat-square) -![Version](https://img.shields.io/badge/api%20version-1.8.1-blue.svg?style=flat-square) +![Version](https://img.shields.io/badge/api%20version-1.9.0-blue.svg?style=flat-square) [![Build Status](https://img.shields.io/travis/com/appwrite/sdk-generator?style=flat-square)](https://travis-ci.com/appwrite/sdk-generator) [![Twitter Account](https://img.shields.io/twitter/follow/appwrite?color=00acee&label=twitter&style=flat-square)](https://twitter.com/appwrite) [![Discord](https://img.shields.io/discord/564160730845151244?label=discord&style=flat-square)](https://appwrite.io/discord) -**This SDK is compatible with Appwrite server version latest. For older versions, please check [previous releases](https://github.com/appwrite/sdk-for-android/releases).** +**This SDK is compatible with Appwrite server version 1.9.x. For older versions, please check [previous releases](https://github.com/appwrite/sdk-for-android/releases).** Appwrite is an open-source backend as a service server that abstracts and simplifies complex and repetitive development tasks behind a very simple to use REST API. Appwrite aims to help you develop your apps faster and in a more secure way. Use the Android SDK to integrate your app with the Appwrite server to easily start interacting with all of Appwrite backend APIs and tools. For full API documentation and tutorials go to [https://appwrite.io/docs](https://appwrite.io/docs) @@ -38,7 +38,7 @@ repositories { Next, add the dependency to your project's `build.gradle(.kts)` file: ```groovy -implementation("io.appwrite:sdk-for-android:13.0.0") +implementation("io.appwrite:sdk-for-android:14.0.0") ``` ### Maven @@ -49,7 +49,7 @@ Add this to your project's `pom.xml` file: io.appwrite sdk-for-android - 13.0.0 + 14.0.0 ``` diff --git a/library/src/main/java/io/appwrite/Client.kt b/library/src/main/java/io/appwrite/Client.kt index 79bf1a28..c894033e 100644 --- a/library/src/main/java/io/appwrite/Client.kt +++ b/library/src/main/java/io/appwrite/Client.kt @@ -87,8 +87,8 @@ class Client @JvmOverloads constructor( "x-sdk-name" to "Android", "x-sdk-platform" to "client", "x-sdk-language" to "android", - "x-sdk-version" to "13.0.0", - "x-appwrite-response-format" to "1.8.0" + "x-sdk-version" to "14.0.0", + "x-appwrite-response-format" to "1.9.0" ) config = mutableMapOf() @@ -168,6 +168,51 @@ class Client @JvmOverloads constructor( return this } + /** + * Set ImpersonateUserId + * + * Impersonate a user by ID on an already user-authenticated request. Requires the current request to be authenticated as a user with impersonator capability; X-Appwrite-Key alone is not sufficient. Impersonator users are intentionally granted users.read so they can discover a target before impersonation begins. Internal audit logs still attribute actions to the original impersonator and record the impersonated target only in internal audit payload data. + * + * @param {string} impersonateuserid + * + * @return this + */ + fun setImpersonateUserId(value: String): Client { + config["impersonateUserId"] = value + addHeader("x-appwrite-impersonate-user-id", value) + return this + } + + /** + * Set ImpersonateUserEmail + * + * Impersonate a user by email on an already user-authenticated request. Requires the current request to be authenticated as a user with impersonator capability; X-Appwrite-Key alone is not sufficient. Impersonator users are intentionally granted users.read so they can discover a target before impersonation begins. Internal audit logs still attribute actions to the original impersonator and record the impersonated target only in internal audit payload data. + * + * @param {string} impersonateuseremail + * + * @return this + */ + fun setImpersonateUserEmail(value: String): Client { + config["impersonateUserEmail"] = value + addHeader("x-appwrite-impersonate-user-email", value) + return this + } + + /** + * Set ImpersonateUserPhone + * + * Impersonate a user by phone on an already user-authenticated request. Requires the current request to be authenticated as a user with impersonator capability; X-Appwrite-Key alone is not sufficient. Impersonator users are intentionally granted users.read so they can discover a target before impersonation begins. Internal audit logs still attribute actions to the original impersonator and record the impersonated target only in internal audit payload data. + * + * @param {string} impersonateuserphone + * + * @return this + */ + fun setImpersonateUserPhone(value: String): Client { + config["impersonateUserPhone"] = value + addHeader("x-appwrite-impersonate-user-phone", value) + return this + } + /** * Set self Signed * diff --git a/library/src/main/java/io/appwrite/models/Document.kt b/library/src/main/java/io/appwrite/models/Document.kt index 830fe384..c55e6d26 100644 --- a/library/src/main/java/io/appwrite/models/Document.kt +++ b/library/src/main/java/io/appwrite/models/Document.kt @@ -17,7 +17,7 @@ data class Document( * Document sequence ID. */ @SerializedName("\$sequence") - val sequence: Long, + val sequence: String, /** * Collection ID. @@ -69,7 +69,7 @@ data class Document( companion object { operator fun invoke( id: String, - sequence: Long, + sequence: String, collectionId: String, databaseId: String, createdAt: String, @@ -93,7 +93,7 @@ data class Document( nestedType: Class ) = Document( id = map["\$id"] as String, - sequence = (map["\$sequence"] as Number).toLong(), + sequence = map["\$sequence"] as String, collectionId = map["\$collectionId"] as String, databaseId = map["\$databaseId"] as String, createdAt = map["\$createdAt"] as String, diff --git a/library/src/main/java/io/appwrite/models/Log.kt b/library/src/main/java/io/appwrite/models/Log.kt index c2df960f..fe8c60b3 100644 --- a/library/src/main/java/io/appwrite/models/Log.kt +++ b/library/src/main/java/io/appwrite/models/Log.kt @@ -14,19 +14,19 @@ data class Log( val event: String, /** - * User ID. + * User ID of the actor recorded for this log. During impersonation, this is the original impersonator, not the impersonated target user. */ @SerializedName("userId") val userId: String, /** - * User Email. + * User email of the actor recorded for this log. During impersonation, this is the original impersonator. */ @SerializedName("userEmail") val userEmail: String, /** - * User Name. + * User name of the actor recorded for this log. During impersonation, this is the original impersonator. */ @SerializedName("userName") val userName: String, diff --git a/library/src/main/java/io/appwrite/models/Row.kt b/library/src/main/java/io/appwrite/models/Row.kt index 793d2782..488ec7bc 100644 --- a/library/src/main/java/io/appwrite/models/Row.kt +++ b/library/src/main/java/io/appwrite/models/Row.kt @@ -17,7 +17,7 @@ data class Row( * Row sequence ID. */ @SerializedName("\$sequence") - val sequence: Long, + val sequence: String, /** * Table ID. @@ -69,7 +69,7 @@ data class Row( companion object { operator fun invoke( id: String, - sequence: Long, + sequence: String, tableId: String, databaseId: String, createdAt: String, @@ -93,7 +93,7 @@ data class Row( nestedType: Class ) = Row( id = map["\$id"] as String, - sequence = (map["\$sequence"] as Number).toLong(), + sequence = map["\$sequence"] as String, tableId = map["\$tableId"] as String, databaseId = map["\$databaseId"] as String, createdAt = map["\$createdAt"] as String, diff --git a/library/src/main/java/io/appwrite/models/User.kt b/library/src/main/java/io/appwrite/models/User.kt index e9a11443..a76d61f0 100644 --- a/library/src/main/java/io/appwrite/models/User.kt +++ b/library/src/main/java/io/appwrite/models/User.kt @@ -121,6 +121,18 @@ data class User( @SerializedName("accessedAt") val accessedAt: String, + /** + * Whether the user can impersonate other users. + */ + @SerializedName("impersonator") + var impersonator: Boolean?, + + /** + * ID of the original actor performing the impersonation. Present only when the current request is impersonating another user. Internal audit logs attribute the action to this user, while the impersonated target is recorded only in internal audit payload data. + */ + @SerializedName("impersonatorUserId") + var impersonatorUserId: String?, + ) { fun toMap(): Map = mapOf( "\$id" to id as Any, @@ -142,6 +154,8 @@ data class User( "prefs" to prefs.toMap() as Any, "targets" to targets.map { it.toMap() } as Any, "accessedAt" to accessedAt as Any, + "impersonator" to impersonator as Any, + "impersonatorUserId" to impersonatorUserId as Any, ) companion object { @@ -165,6 +179,8 @@ data class User( prefs: Preferences>, targets: List, accessedAt: String, + impersonator: Boolean?, + impersonatorUserId: String?, ) = User>( id, createdAt, @@ -185,6 +201,8 @@ data class User( prefs, targets, accessedAt, + impersonator, + impersonatorUserId, ) @Suppress("UNCHECKED_CAST") @@ -211,6 +229,8 @@ data class User( prefs = Preferences.from(map = map["prefs"] as Map, nestedType), targets = (map["targets"] as List>).map { Target.from(map = it) }, accessedAt = map["accessedAt"] as String, + impersonator = map["impersonator"] as? Boolean, + impersonatorUserId = map["impersonatorUserId"] as? String, ) } } \ No newline at end of file