home / skills / hyperb1iss / hyperdroid-skill / android-build

android-build skill

/skills/android-build

This skill helps you build Android apps and custom ROMs using Gradle CLI and AOSP/LineageOS workflows.

npx playbooks add skill hyperb1iss/hyperdroid-skill --skill android-build

Review the files below or copy the command above to add this skill to your agents.

Files (3)
SKILL.md
9.2 KB
---
name: android-build
description: Use when building Android apps (Gradle CLI) or ROMs (AOSP, LineageOS). Triggers on "gradle build", "assemble", "AOSP", "LineageOS", "lunch", "mka", "breakfast", "brunch", "compile android", "device tree", "kernel build".
---

# Android Build Systems

This skill covers building Android apps via Gradle CLI and building custom ROMs via AOSP/LineageOS.

---

## App Building (Gradle CLI)

### Essential Commands

```bash
./gradlew tasks                     # List available tasks
./gradlew assembleDebug             # Build debug APK
./gradlew assembleRelease           # Build release APK
./gradlew installDebug              # Build + install to device
./gradlew bundleRelease             # Build AAB (App Bundle)

# APK output location
# app/build/outputs/apk/debug/app-debug.apk
# app/build/outputs/apk/release/app-release.apk
```

### Build Variants

```bash
./gradlew assembleFreeDebug         # Flavor + build type
./gradlew assemblePaidRelease
./gradlew assembleDebug --info      # Verbose output
./gradlew assembleRelease -x test   # Skip tests
```

### Testing

```bash
./gradlew test                      # Unit tests
./gradlew testDebugUnitTest         # Debug unit tests only
./gradlew connectedAndroidTest      # Instrumented tests
./gradlew connectedCheck            # All connected tests

# Run specific test
./gradlew test --tests "*.MyTestClass"
```

### Linting & Analysis

```bash
./gradlew lint                      # Run lint
./gradlew lintDebug                 # Debug only (faster)
./gradlew ktlintCheck               # Kotlin style (if configured)
./gradlew detekt                    # Detekt analysis (if configured)
```

### Clean & Refresh

```bash
./gradlew clean                     # Clean build
./gradlew clean assembleDebug       # Clean + build
./gradlew --refresh-dependencies    # Force dependency refresh
./gradlew --stop                    # Stop Gradle daemon
```

### Dependencies

```bash
./gradlew dependencies              # All dependencies
./gradlew app:dependencies          # Module dependencies
./gradlew dependencyInsight --dependency <name>
```

### Signing

Debug keystore location:

- Linux: `~/.android/debug.keystore`
- macOS: `~/.android/debug.keystore`
- Windows: `C:\Users\<user>\.android\debug.keystore`

Password: `android`, Alias: `androiddebugkey`

```bash
# Create release keystore
keytool -genkey -v -keystore release.keystore \
    -alias my-key-alias -keyalg RSA -keysize 2048 -validity 10000
```

### Performance

```bash
./gradlew assembleDebug --parallel  # Parallel builds
./gradlew assembleDebug --build-cache  # Use cache
./gradlew assembleDebug --offline   # Offline mode
./gradlew --scan                    # Build scan (uploads data)
./gradlew --profile                 # Local profile report
```

### gradle.properties Optimization

```properties
org.gradle.jvmargs=-Xmx4g -XX:+HeapDumpOnOutOfMemoryError
org.gradle.parallel=true
org.gradle.caching=true
org.gradle.configuration-cache=true
android.useAndroidX=true
```

---

## SDK Management

### sdkmanager

```bash
sdkmanager --list                   # List available packages
sdkmanager --list | grep system     # Filter system images
sdkmanager "platform-tools"         # Install package
sdkmanager "platforms;android-34"   # Install platform
sdkmanager "system-images;android-34;google_apis;x86_64"
sdkmanager --update                 # Update all
sdkmanager --licenses               # Accept licenses
```

### avdmanager

```bash
avdmanager list device              # List device profiles
avdmanager list avd                 # List created AVDs

# Create AVD
avdmanager create avd -n my_avd \
    -k "system-images;android-34;google_apis;x86_64" \
    -d pixel_6

avdmanager delete avd -n my_avd
```

### Emulator CLI

```bash
emulator -list-avds                 # List AVDs
emulator @my_avd                    # Start AVD
emulator @my_avd -no-snapshot       # Fresh boot
emulator @my_avd -no-window         # Headless
emulator @my_avd -wipe-data         # Factory reset
```

---

## ROM Building (AOSP/LineageOS)

### Environment Setup

```bash
# Install repo tool
mkdir -p ~/.bin
curl https://storage.googleapis.com/git-repo-downloads/repo > ~/.bin/repo
chmod a+x ~/.bin/repo
export PATH="$HOME/.bin:$PATH"

# Initialize repo
mkdir android && cd android
repo init -u https://github.com/LineageOS/android.git -b lineage-21.0
# Or AOSP: repo init -u https://android.googlesource.com/platform/manifest

# Sync source
repo sync -c -j$(nproc) --force-sync --no-tags --no-clone-bundle
```

### Build Commands

```bash
# Setup environment
source build/envsetup.sh

# Select device
lunch <device>-userdebug           # AOSP
breakfast <device>                  # LineageOS

# Build
m                                   # Full build
mka bacon                           # LineageOS (with flashable zip)
mka bootimage                       # Just boot.img
mka systemimage                     # Just system

# Parallel build
m -j$(nproc)
```

### Build Variants

| Variant     | Purpose                                |
| ----------- | -------------------------------------- |
| `user`      | Production, no root, limited debugging |
| `userdebug` | Like user + root + debugging           |
| `eng`       | Development, all debug tools           |

### Common Targets

```bash
m bootimage                         # Kernel + ramdisk
m systemimage                       # System partition
m vendorimage                       # Vendor partition
m otapackage                        # OTA zip
mka bacon                           # LineageOS flashable zip

# Module-specific
m Settings                          # Just Settings app
mm                                  # Build current directory
mmm packages/apps/Settings          # Build specific path
```

### LineageOS Specifics

```bash
breakfast <device>                  # Setup + sync device deps
brunch <device>                     # breakfast + mka bacon

# Cherry-pick from Gerrit
repopick <change_number>
repopick -t <topic>

# Sync specific project
repo sync packages/apps/Settings
```

### Build Output

```
out/target/product/<device>/
├── boot.img                        # Kernel + ramdisk
├── system.img                      # System partition
├── vendor.img                      # Vendor partition
├── lineage-*.zip                   # Flashable zip (LineageOS)
└── recovery.img                    # Recovery (non-A/B)
```

---

## Device Trees

### Structure

```
device/<vendor>/<device>/
├── AndroidProducts.mk              # Product makefiles list
├── BoardConfig.mk                  # Board configuration
├── device.mk                       # Device makefile
├── lineage_<device>.mk             # LineageOS product
├── extract-files.sh                # Vendor blob extraction
├── proprietary-files.txt           # Blob list
├── sepolicy/                       # SELinux policies
└── overlay/                        # Resource overlays
```

### Key Files

**BoardConfig.mk** - Hardware configuration:

```makefile
TARGET_ARCH := arm64
TARGET_BOARD_PLATFORM := <platform>
TARGET_BOOTLOADER_BOARD_NAME := <device>
BOARD_KERNEL_CMDLINE := ...
BOARD_BOOT_HEADER_VERSION := 4
```

**device.mk** - Device packages:

```makefile
PRODUCT_PACKAGES += \
    [email protected] \
    audio.primary.$(TARGET_BOARD_PLATFORM)

PRODUCT_COPY_FILES += \
    $(LOCAL_PATH)/configs/audio_policy.conf:...
```

---

## Kernel Building

### Standalone

```bash
# Setup
export ARCH=arm64
export CROSS_COMPILE=aarch64-linux-gnu-
# Or for Clang:
export CC=clang
export CLANG_TRIPLE=aarch64-linux-gnu-

# Configure
make <device>_defconfig

# Build
make -j$(nproc)

# Output
arch/arm64/boot/Image.gz
```

### In AOSP Tree

```makefile
# In BoardConfig.mk
TARGET_KERNEL_SOURCE := kernel/<vendor>/<device>
TARGET_KERNEL_CONFIG := <device>_defconfig
TARGET_KERNEL_CLANG_COMPILE := true
```

---

## Troubleshooting

### Common Gradle Issues

```bash
# OOM
export GRADLE_OPTS="-Xmx4g"

# Daemon issues
./gradlew --stop
rm -rf ~/.gradle/daemon

# Cache issues
./gradlew clean --refresh-dependencies
```

### Common AOSP Issues

```bash
# Ninja error - usually dependency issue
m clean && m

# Jack server (old builds)
./prebuilts/sdk/tools/jack-admin kill-server
./prebuilts/sdk/tools/jack-admin start-server

# SELinux issues
audit2allow -i audit.log
```

### Build Logs

```bash
# Gradle
./gradlew assembleDebug --stacktrace
./gradlew assembleDebug --info

# AOSP
m 2>&1 | tee build.log
```

---

## Quick Reference

### Gradle

| Task          | Command                     |
| ------------- | --------------------------- |
| Build debug   | `./gradlew assembleDebug`   |
| Build release | `./gradlew assembleRelease` |
| Install       | `./gradlew installDebug`    |
| Test          | `./gradlew test`            |
| Lint          | `./gradlew lint`            |
| Clean         | `./gradlew clean`           |
| Dependencies  | `./gradlew dependencies`    |

### AOSP/LineageOS

| Task          | Command                    |
| ------------- | -------------------------- |
| Setup env     | `source build/envsetup.sh` |
| Select device | `lunch <device>-userdebug` |
| Full build    | `m`                        |
| LineageOS zip | `mka bacon`                |
| Just boot     | `mka bootimage`            |
| Sync          | `repo sync -c -j$(nproc)`  |

Overview

This skill helps build Android apps with the Gradle CLI and compile Android ROMs (AOSP/LineageOS) including device trees and kernels. It provides the common commands, workflow steps, and troubleshooting tips you need to run reliable local builds and speed up iterative development. Use it to run tasks, manage SDK/AVD, produce flashable ROMs, and diagnose build failures.

How this skill works

The skill maps natural triggers (e.g., "gradle build", "AOSP", "lunch", "mka", "brunch") to concrete commands and recommended flags. It outlines Gradle tasks, SDK/emulator management, repo initialization and sync, lunch/breakfast flows for device selection, and common m/mka targets for ROM outputs. It also covers device tree layout, kernel build steps, signing, caching and profiling options to optimize build time.

When to use it

  • Building Android apps or app bundles with Gradle (assemble, bundle, install).
  • Running unit or instrumented tests and lint/analysis tasks for Android projects.
  • Initializing, syncing or compiling AOSP or LineageOS source trees.
  • Producing flashable ROM zips, system/boot/vendor images, or kernel builds for devices.
  • Managing SDK packages, creating AVDs and running emulators locally.
  • Troubleshooting build errors, OOM, dependency and SELinux issues.

Best practices

  • Use org.gradle.jvmargs and configuration-cache in gradle.properties to reduce OOM and improve performance.
  • Run repo sync with -c and -j$(nproc) and prefer --force-sync only when needed to avoid partial sync issues.
  • Isolate builds with clean + assemble when debugging, and use --refresh-dependencies to fix stale artifacts.
  • Build modules with mm/mmm for faster iteration instead of full m when changing single packages.
  • Keep a signed release keystore securely stored and never commit it; use debug keystore only for local testing.

Example use cases

  • Build and install a debug APK: ./gradlew assembleDebug && ./gradlew installDebug.
  • Create an AVD and run headless emulator for CI tests: avdmanager create avd ... && emulator @my_avd -no-window.
  • Initialize and sync LineageOS source, then build a flashable zip: repo init ... && repo sync ... && brunch <device>.
  • Compile only kernel or boot image: export CROSS_COMPILE=... && make <device>_defconfig && make -j$(nproc).
  • Run focused builds for a single app: mmm packages/apps/Settings or mm in the app directory.

FAQ

How do I reduce Gradle memory errors?

Increase org.gradle.jvmargs in gradle.properties (e.g., -Xmx4g) and enable org.gradle.caching and parallel builds when appropriate.

When should I use m vs mka vs mm?

Use m for full tree builds, mka for parallel LineageOS-targeted builds (bacon/zip), and mm/mmm to compile only the current module or specific paths for faster iteration.