Skip to content

fix(android): isolate realtime connections by client - #2139

Merged
ChiragAgg5k merged 4 commits into
mainfrom
fix/android-realtime-isolation
Oct 23, 2026
Merged

ChiragAgg5k merged 4 commits into
mainfrom
fix/android-realtime-isolation

Conversation

@ChiragAgg5k

@ChiragAgg5k ChiragAgg5k commented Oct 23, 2026 •

Copy link
Copy Markdown
Member

Two Android Client objects currently share realtime state through a companion object. Subscribing on a second backend can send its subscription over the first backend’s socket, and lifecycle operations affect subscriptions belonging to other clients.

Give each Client one lazily initialized realtime connection. Realtime wrappers around the same client reuse that connection; separate clients own independent sockets, subscriptions, presence, heartbeat, reconnect state and callbacks. Public wrappers retain independent coroutine scopes so cancelling one cannot permanently disable its client’s connection. The existing subscription overloads remain available.

Realtime handshakes now read the JWT header configured by setJWT(). The previous config lookup used jwt, while that setter stores the config entry under jWT, so it omitted the configured JWT.

Regression coverage uses real WebSocket backends and public SDK APIs. It checks different endpoints, different JWTs on the same endpoint/project, same-client wrapper reuse, presence, error/close callbacks, reconnection, disconnect isolation, and cancellation followed by wrapper recreation. Isolation is a dedicated JUnit test with direct assertEquals/assertTrue assertions, executed by both Android language E2E harnesses, including the R8-shrunk build. It does not print or compare a success marker.

Validation:

  • The old generated SDK fails the regression with second backend must receive its own subscription: expected b, got a.
  • Patched Android 16/JDK 17 E2E passes: 1 test, 295 assertions; Android lint and all 45 R8-shrunk JUnit tests pass, including RealtimeIsolationTest.isolatesClientConnectionsAndLifecycle.
  • Regenerated Android/client output passes ktlint 1.8.0.
  • Targeted PHPStan, repository PHP lint, Rector and Twig lint pass.
  • Standards and behavior reviews found no remaining blockers.

Addresses appwrite/sdk-for-android#102. Regenerate and release the Android SDK after merging to deliver the fix to applications.

Related: appwrite-labs/cloud#6667

@hansi-codes

hansi-codes Bot commented Oct 23, 2026 •

Copy link
Copy Markdown

🟢 Tier S · Ready to merge

Android realtime connections are now lazily owned by each Client, with wrappers for the same client sharing the connection and separate clients maintaining isolated sockets and lifecycle state. The handshake uses the JWT configured through setJWT(). The E2E coverage exercises these behaviors against WebSocket backends, including reconnection, wrapper recreation, and the R8-shrunk build.

Latest changes: The latest commits convert the isolation scenario into a dedicated JUnit test with direct assertions, update both Android harnesses to copy and run it, and remove the former stdout success-marker expectation.

Verdict New comments Fixed Still open
✅ Approved 0 0 0
📂 Walkthrough · 7
File Change
templates/android/library/src/main/java/io/package/Client.kt.twig Adds a lazily initialized realtime connection owned by each client.
templates/android/library/src/main/java/io/package/services/Realtime.kt.twig Uses client-owned realtime state and reads the configured JWT for WebSocket handshakes.
tests/e2e/Android16Java17Test.php Copies and runs the JUnit isolation test in the R8-shrunk Android test run.
tests/e2e/Android5Java17Test.php Copies and runs the JUnit isolation test in the Android 5 test run.
tests/e2e/languages/android/RealtimeIsolationTest.kt Adds direct JUnit coverage for client isolation, wrapper reuse, presence, callbacks, reconnects, and lifecycle operations.
tests/e2e/languages/android/r8-rules.pro Keeps the isolation payload model for the R8-shrunk test.
tests/e2e/languages/android/realtime.gradle.kts Adds MockWebServer for the WebSocket-backed isolation test.

Reviewed the commits since 59ff37e · Details · Comment @hansi-codes review to re-run, or mention @hansi-codes with a question.

@ChiragAgg5k ChiragAgg5k self-assigned this Oct 23, 2026

@hansi-codes hansi-codes Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

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

🟢 Tier S · Looks good to merge. Summary

@ChiragAgg5k
ChiragAgg5k merged commit 1a5b274 into main Oct 23, 2026
61 checks passed
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.

1 participant