Skip to content

[PB-5925]: add native InternxtApiClient for DocumentsProvider#422

Open
terrerox wants to merge 5 commits intorelease-1.9.1from
feature/PB-5925-kotlin-api-client
Open

[PB-5925]: add native InternxtApiClient for DocumentsProvider#422
terrerox wants to merge 5 commits intorelease-1.9.1from
feature/PB-5925-kotlin-api-client

Conversation

@terrerox
Copy link
Copy Markdown

Adds a pure-Kotlin HTTP client that talks directly to the Drive and Bridge APIs so the SAF DocumentsProvider can fetch folder contents and download links without the React Native bridge. Covers list/create/rename/move/trash on Drive (Bearer auth) and getDownloadLinks on Bridge (Basic auth with sha256(userId).hex derivation). Typed errors for 401/404/other/network; MockWebServer tests for parsing, auth headers, gateway-required headers, and error mapping.

Adds a pure-Kotlin HTTP client that talks directly to the Drive and Bridge APIs so the SAF DocumentsProvider can fetch folder contents and download links without the React Native bridge. Covers list/create/rename/move/trash on Drive (Bearer auth) and getDownloadLinks on Bridge (Basic auth with sha256(userId).hex derivation). Typed errors for 401/404/other/network; MockWebServer tests for parsing, auth headers, gateway-required headers, and error mapping.
@terrerox terrerox self-assigned this Apr 20, 2026
@terrerox terrerox requested a review from CandelR April 20, 2026 03:54
@CandelR CandelR requested a review from TamaraFinogina April 23, 2026 11:02
Comment on lines +9 to +10
val clientName: String = "drive-mobile",
val clientVersion: String = "v1.9.0",
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Perhaps we should make this configurable so that there is a single source of truth. Otherwise, we might as well forget about changing it here

private fun driveUrl(path: String) = "${config.driveBaseUrl.trimEnd('/')}/$path".toHttpUrl()
private fun bridgeUrl(path: String) = "${config.bridgeBaseUrl.trimEnd('/')}/$path".toHttpUrl()

private fun execute(request: Request): JSONObject {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think that this fun name could be a little more descriptive

Comment on lines +201 to +216
private fun JSONArray?.orEmpty(): JSONArray = this ?: JSONArray()

private inline fun <T> JSONArray.map(transform: (JSONObject) -> T): List<T> {
val out = ArrayList<T>(length())
for (i in 0 until length()) out.add(transform(getJSONObject(i)))
return out
}

private fun JSONObject.optStringOrNull(key: String): String? =
if (isNull(key)) null else optString(key).takeIf { it.isNotEmpty() }

private fun JSONObject.optLongFlexible(key: String): Long = when (val v = opt(key)) {
is Number -> v.toLong()
is String -> v.toLongOrNull() ?: 0L
else -> 0L
}
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Perhaps I would extract these functions and add some tests


import java.security.MessageDigest

object HashUtil {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

add @TamaraFinogina as codeowner for crypto directory please :)

import org.junit.Before
import org.junit.Test

class InternxtApiClientTest {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would add more tests, for example for listFolderFolders, createFolder, null optional fields in parseFile/parseFolder, size as a string value, and 5xx ApiError

  - Wire AuthConfig.clientName/clientVersion through
    BuildConfig.INTERNXT_CLIENT_NAME and BuildConfig.INTERNXT_CLIENT_VERSION,
    populated by app/build.gradle from package.json. package.json is now the
    single source of truth for the internxt-client/internxt-version headers.
  - Extract JSON helpers (orEmpty, map, optStringOrNull, optLongFlexible)
    from InternxtApiClient into JsonExtensions.kt; cover each branch in a
    new JsonExtensionsTest.
  - Rename InternxtApiClient.execute -> executeApiRequest.
  - Expand InternxtApiClientTest: listFolderFolders, createFolder, null
    optional fields, size given as a string, and 5xx -> ApiError. Add an
    enqueueJson helper to cut response-stub boilerplate.
  - Add @TamaraFinogina as CODEOWNER for the new documents/crypto/ directory.
@terrerox terrerox requested a review from CandelR April 24, 2026 03:52
@sonarqubecloud
Copy link
Copy Markdown

Base automatically changed from feature/PB-5924-scaffold-documents-provider-v2 to release-1.9.1 April 24, 2026 04:19
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants