vojo/docs/ai/android.md

3.5 KiB

Android (Capacitor)

Requirements

  • Node >= 22
  • JDK 17+ (21 used in practice)
  • Android SDK with platform 36 + build-tools 36.0.0
  • SDK location: /usr/lib/android-sdk, also set in android/local.properties

Config

  • capacitor.config.tsappId: chat.vojo.app, webDir: dist
  • android/ — generated Android Studio project, targetSdkVersion 36, compileSdkVersion 36, minSdkVersion 24

Build scripts

npm run build:android:debug    # full chain: build → sync → debug APK
npm run build:android:release  # full chain: build → sync → release APK
npm run build:android:aab      # full chain: build → sync → release AAB
npm run android:sync           # sync dist/ → android assets
npm run android:apk:debug      # gradle debug build only

APK output: android/app/build/outputs/apk/debug/app-debug.apk

Versioning

versionCode and versionName are derived from git describe --tags --match 'v*' in android/app/build.gradle, mirroring resolveAppVersion() in vite.config.js so the APK's versionName matches __APP_VERSION__ shown in About. Tag is v0.2.0; patch is the commit count since that tag (e.g. v0.2.0-87-g… → versionName 0.2.87). When git is unavailable, falls back to package.json version.

versionCode = major * 1_000_000 + minor * 1_000 + patch

Key architecture decisions

  • Bundled build. dist/ is copied into the APK — not loaded remotely in a WebView.
  • Service Worker stays active. Critical for authenticated Matrix media (MSC3916 / Matrix spec v1.11+). DO NOT disable. resolveServiceWorkerRequests default true.
  • Edge-to-edge. EdgeToEdge.enable() in MainActivity.java + windowLayoutInDisplayCutoutMode: shortEdges.
  • External links. Opened via @capacitor/browser plugin — see src/app/utils/capacitor.ts.
  • Safe-area coloring. body background-color is bound to the folds theme variable var(--oq6d070) for consistent safe-area coloring.
  • Safe-area insets. Applied on #root (not body) so the theme background extends behind the system bars.

VSCode tasks

See .vscode/tasks.json:

  • Deploy to vojo.chat (Ctrl+Shift+D) — web deploy
  • Deploy to Android (ADB) (Ctrl+Shift+A) — build + adb install

Push string resources (generated)

Push notification text for Android is generated from public/locales/{en,ru}.json (namespace Push) by scripts/gen-push-strings.mjs. The Gradle build runs this automatically via GeneratePushStringsTask registered in android/app/build.gradle through AGP addGeneratedSourceDirectory — output goes to build/generated/res/push/<variant>/values{,-ru}/push_strings.xml. No manual step needed; ./gradlew assembleDebug handles it.

The task requires node in PATH. Terminal builds and CI inherit it from the shell. macOS Android Studio with nvm/fnm: the GUI app may not see nvm-managed node. Workaround: set NODE_BIN=/path/to/node in android/gradle.properties (the task reads it via project.findProperty('NODE_BIN')) or launch AS from a shell that sources your node manager (open -a "Android Studio").

ADB wireless workflow

  1. On the phone, enable Wireless debugging, tap "Pair device with pairing code" — note IP, port, 6-digit code.
  2. adb pair <ip>:<pair-port> <code>
  3. adb connect <ip>:<connect-port>

The pair port and the connect port are different — don't mix them up.