Build, install and test Kotlin + Jetpack Compose Android apps entirely on an Android phone, inside Termux. No Android Studio, no PC, no root, no proot.
Everything is built from Termux packages and Google's official Android SDK. There are no third-party repositories, prebuilt binaries, vendored wrappers or curl-pipe-to-shell installers.
One line:
pkg install -y git && git clone --depth 1 https://github.com/mhs003/TAD ~/.local/share/TAD && ~/.local/share/TAD/bin/tad-setupThen source ~/.bashrc and check it over with tad doctor.
The installer installs the Termux packages, downloads Google's SDK command-line
tools, accepts the SDK licences, installs the platform and build-tools, writes
env.sh, hooks it into ~/.bashrc, and configures ~/.gradle/gradle.properties.
It is idempotent, so re-run it any time. ./install.sh does the same thing if
you would rather not paste a one-liner.
| Command | Description |
|---|---|
tad setup |
Build the complete toolchain from an empty Termux |
tad doctor |
Check the toolchain and report problems |
tad new <name> [--package <id>] [--dir <path>] |
Create a Kotlin + Compose project |
tad init [dir] |
Make an existing project buildable on-device |
tad build [debug|release] |
Assemble an APK and verify its contents |
tad compile [debug|release|all] |
Compile Kotlin sources without packaging an APK |
tad run [--log] |
Build, install and launch on the device |
tad install [apk] |
Install an APK on the device |
tad test [unit|instrumented|all] |
Run JVM and/or on-device tests |
tad clean [--daemon|--all] |
Clean build output |
tad adb <cmd> |
adb helpers — run tad adb for the list |
tad new MyApp --package com.example.myapp
cd MyApp
tad compile # fast typecheck, no APK
tad build # assembleDebug + APK verification
tad run # build, install, launch
tad test unit # JVM unit tests
tad test instrumented # Compose UI tests on the deviceTermux and adb run on the same phone, so adb talks to 127.0.0.1.
- Enable Developer options → Wireless debugging.
- Pair device with pairing code — note the pairing port and code.
tad adb pair <pairing-port> <code>- Note IP address & Port, then
tad adb connect <connect-port> tad adb statusto confirm.
Useful extras:
tad adb tcpip 5555— pin adbd to a fixed port until reboot.tad adb phantom off— disable Android's phantom-process killer for long builds. Re-enable it afterwards (tad adb phantom on); leaving it off can drain the battery.
On some OEM ROMs the shell user shares the device with a secondary user (for
example TECNO's "Dual Space", user 999). Every command here targets --user 0
explicitly, so package queries and installs behave predictably.
All versions live in tad.conf. Each value comes from one of:
| Source | Used for |
|---|---|
| Termux packages | openjdk-21, gradle, kotlin, aapt2, apksigner, d8, android-tools |
Google SDK (dl.google.com via sdkmanager) |
command-line tools, platform-tools, platforms;android-37.2, build-tools;36.0.0 |
| Maven (Google Maven + Maven Central, resolved by Gradle) | AGP, Compose, AndroidX |
Change a value and re-run tad setup (SDK levels) or tad init (per project).
An Android build is almost entirely Java, which is architecture-independent. The
exceptions are the native binaries in build-tools and platform-tools, which
ship as x86-64 and cannot execute on an ARM device.
- aapt2 — AGP is pointed at Termux's native aarch64
aapt2viaandroid.aapt2FromMavenOverride. This was verified against every AGP 9 resource task, includingoptimizeReleaseResourceswith R8 minification and resource shrinking enabled. - adb —
platform-tools/adbis replaced with a symlink to Termux's aarch64 adb, so AGP's on-device tests work. Neitherplatform-toolsnorbuild-toolsis put onPATH; their natives would only shadow the working Termux copies. - Kotlin — AGP 9 compiles Kotlin itself ("built-in Kotlin"), so the
org.jetbrains.kotlin.androidplugin is not applied. The only Kotlin plugin in the generated project is the Compose compiler, whose version must match the Kotlin Gradle plugin AGP bundles.
TAD/
├── tad.conf versions and paths
├── env.sh generated by tad setup, sourced from ~/.bashrc
├── lib/common.sh shared helpers
├── bin/ the tad-* commands
├── templates/compose-app/ Kotlin + Compose project template
└── .agents/skills/tad/ Agent Skill so coding agents can drive this tool
└── SKILL.md
The bundled Agent Skill teaches any Agent-Skills-compatible coding agent how to
drive tad. It lives at .agents/skills/tad/, and copying it to
~/.agents/skills/ makes it available in other projects.
| Symptom | Cause / fix |
|---|---|
Exec format error from adb or aapt2 |
An x86-64 SDK binary is shadowing the Termux one. Run tad doctor; re-run tad setup to restore the adb symlink. |
| Build killed part-way through | Android's phantom-process killer. tad adb phantom off, then re-enable when done. |
OutOfMemoryError during a build |
Lower GRADLE_JVMARGS in tad.conf, then tad setup. |
BUILD SUCCESSFUL but the app will not install |
tad build guards this already — it checks the APK for AndroidManifest.xml, resources.arsc and dex, and runs apksigner verify. |
WARNING: ... 'android.aapt2FromMavenOverride' is experimental |
Expected. AGP marks the option experimental; it is required for on-device builds. |
| Gradle daemon misbehaving | tad clean --daemon. |
This project is licensed under the MIT License.