AndroidSDK

repository·master·Indexed 23 days ago

https://github.com/thyrlian/androidsdk

A Docker-based Android development environment designed for consistency across machines and CI/CD pipeline integration. It provides a minimal Android SDK, Gradle, and the Kotlin compiler, with support for persistent SDK volumes, Gradle cache optimization, and non-interactive license acceptance. The project also includes a VNC-enabled image for running Android emulators and a Gradle distributions mirror server to optimize build speeds.

Tokens
6.5K
Snippets
16
Records
26
Agent score
30%

What's inside AndroidSDK

  1. Overview of AndroidSDK Docker Image

    master

    AndroidSDK is a Docker image providing a complete Android SDK development environment. It is designed to solve the "works on my machine" problem and provide a consistent environment for Android CI builds.

    Key Features:

    • Contains the barebone official minimal Android SDK.
    • Provides maximum flexibility by allowing you to tailor SDK tools for your specific project.
    • Supports mounting an external persistent SDK directory to avoid repeated downloads.
    • Includes Gradle and the Kotlin compiler for convenience, though using the Gradle Wrapper is highly recommended for reliable builds.
  2. Configure JVM options via environment variables

    master

    When you need to pass arguments to a Java executable without modifying the launch command, use the following environment variables:

    • JAVA_TOOL_OPTIONS: The official way to augment a command line. Recognized by all VMs. Use this to inject flags like -Xmx or -Xms globally.
    • _JAVA_OPTIONS: Specifically used to pass options to the JVM (often used for container awareness in older JDKs).
    • JAVA_OPTS: Note that the JVM does not use this variable directly. It is a convention used by other applications (like Tomcat). To use it for a manual command, you must explicitly include it: java $JAVA_OPTS ....
  3. Parallelize UI tests with shards

    master

    When running tests on Firebase Test Lab via gcloud, you can distribute test cases across multiple devices to speed up execution using sharding. Use the --num-uniform-shards flag to specify the number of shards.

    For example, to run 20 tests in parallel across 4 devices (resulting in 5 tests per device), set --num-uniform-shards=4.

  4. Set up a local Gradle Distributions Mirror Server

    master

    To optimize build speeds and reduce network bandwidth, you can run a local mirror for Gradle distributions.

    Workflow:

    1. Build the mirror image: Use docker build -t gradle-server gradle-server. You can pass --build-arg GRADLE_DOWNLOAD_AMOUNT=<amount> to specify how many distributions to pre-download.
    2. Download distributions locally: Run the provided gradle-server/gradle-downloader.sh on your host machine to populate a directory.
    3. Run the mirror: Start the gradle-server container, mounting your local download directory to /var/www/gradle.org/public_html/distributions.
    4. Configure the AndroidSDK container to use the mirror:
      • Copy the SSL certificate from the gradle-server container to the host, then to the AndroidSDK container.
      • Import the certificate into the AndroidSDK container's Java keystore using keytool.
      • Map services.gradle.org to your local IP in the container's /etc/hosts file.

    Alternative (No SSL): If you want to avoid SSL configuration, change the distributionUrl in your project's gradle/wrapper/gradle-wrapper.properties from https to http.

    # 1. Build the mirror
    docker build -t gradle-server gradle-server
    
    # 2. Download distributions locally
    gradle-server/gradle-downloader.sh [DOWNLOAD_DIRECTORY] [DOWNLOAD_AMOUNT]
    
    # 3. Run the mirror
    docker run -d -p 80:80 -p 443:443 -v [DOWNLOAD_DIRECTORY]:/var/www/gradle.org/public_html/distributions gradle-server
    
    # 4. Configure AndroidSDK container
    docker cp `docker ps -aqf "ancestor=gradle-server"`:/etc/apache2/ssl/apache.crt apache.crt
    docker cp apache.crt `docker ps -aqf "ancestor=thyrlian/android-sdk"`:/home/apache.crt
    
    docker exec -it `docker ps -aqf "ancestor=thyrlian/android-sdk"` bash -c '$JAVA_HOME/bin/keytool -import -trustcacerts -file /home/apache.crt -keystore $JAVA_HOME/jre/lib/security/cacerts -storepass changeit -noprompt'
    
    docker exec -it `docker ps -aqf "ancestor=thyrlian/android-sdk"` bash -c 'echo "[YOUR_HOST_IP_ADDRESS_FOR_GRADLE_CONTAINER] services.gradle.org" >> /etc/hosts'
  5. Install required Android SDK packages

    master

    Before running an emulator, ensure the necessary SDK components are installed. If you encounter errors regarding ANDROID_SDK_ROOT or ANDROID_HOME, you likely need to install platform-tools, the specific platform API level, and the emulator package.

    Use sdkmanager to list available packages and install them as needed.

    sdkmanager "platform-tools" "platforms;android-<api_level>" "emulator"
    
    # To list available images:
    sdkmanager --list --verbose
  6. Follow the Release Guide

    master

    To release a new version of the Android SDK image, follow these steps from the project root:

    1. Publish the image: Run the publisher script with a tag. ./image-publisher.sh [TAG]

    2. Inspect tool versions: Run the version-inspector.sh script inside a Docker container to verify the versions of the tools included in the image. cmd=$(cat ./android-sdk/version-inspector.sh) && docker run -it --rm android-sdk bash -c "$cmd"

    3. Update Changelog: Use the version information printed by the previous commands to update the CHANGELOG.md.

    4. Tag in Git: Create a new Git tag named after the version (e.g., x.x) and publish it.

  7. Preconditions for running x86 Android Emulators

    master

    To run x86 emulators with hardware acceleration (KVM), your host machine must support virtualization.

    1. Verify CPU support: Check if your CPU supports vmx (Intel) or svm (AMD) by running:

      grep -cw ".*\(vmx\|svm\).*" /proc/cpuinfo

      A non-zero result indicates support.

    2. Verify KVM status: Use sudo kvm-ok to ensure KVM acceleration can be used.

    3. Load KVM modules: If not loaded, use sudo modprobe kvm (or kvm-intel / kvm-amd depending on your processor).

    Note: x86 emulators require KVM and are primarily runnable on Linux. ARM emulators are host-independent but have lower performance.

    grep -cw ".*\(vmx\|svm\).*" /proc/cpuinfo
  8. Share Android SDK via NFS

    master

    To host the Android SDK in a single location and share it across multiple containers, use a Network File System (NFS).

    Approaches:

    • Mount the NFS onto your host machine, then use the Docker -v flag to mount the host directory into the container.
    • Use a Docker volume plugin like Convoy.

    NFS Server Setup (Ubuntu):

    1. Install nfs-kernel-server.
    2. Create the directory /var/nfs/android-sdk.
    3. Download and unzip the Android tools into that directory.
    4. Create a licenses directory and add the required license files.
    5. Configure /etc/exports to allow access and restart the service.
    # Ubuntu NFS Server Setup
    sudo apt-get update
    sudo apt-get install -y nfs-kernel-server
    sudo mkdir -p /var/nfs/android-sdk
    
    # Download and setup SDK
    cd /var/nfs/android-sdk
    sudo apt-get install -y wget zip
    sudo wget -q $(wget -q -O- 'https://developer.android.com/sdk' | grep -o "\"https://.*android.*tools.*linux.*\"" | sed "s/\"//g")
    sudo unzip *tools*linux*.zip
    sudo rm *tools*linux*.zip
    sudo mkdir licenses
    echo 8933bad161af4178b1185d1a37fbf41ea5269c55 | sudo tee licenses/android-sdk-license > /dev/null
    echo 84831b9409646a918e30573bab4c9c91346d8abd | sudo tee licenses/android-sdk-preview-license > /dev/null
    echo d975f751698a77b662f1254ddbeed3901e976f5a | sudo tee licenses/intel-android-extra-license > /dev/null
    
    # Configure exports
    sudo chown nobody:nogroup /var/nfs
    echo "/var/nfs         *(rw,sync,no_subtree_check,no_root_squash)" | sudo tee --append /etc/exports > /dev/null
    sudo exportfs -a
    sudo service nfs-kernel-server start
  9. Access the container desktop via VNC

    master

    To run an Android emulator inside the container, you may need remote desktop access via VNC.

    1. Pull the VNC-enabled image: thyrlian/android-sdk-vnc.
    2. Run the container mapping port 5901 (VNC) and 2222 (SSH).
    3. Connect using a VNC client to <container_ip_address>:5901.

    Credentials:

    • Password (control): android
    • Password (view only): docker

    Recommended Clients:

    • macOS: Screen Sharing
    • Linux: Remmina
    • Cross-Platform: VNC Viewer

    Example: Launching an emulator inside VNC:

    echo "no" | avdmanager create avd -n test -k "system-images;android-25;google_apis;armeabi-v7a"
    emulator -avd test -no-audio -no-boot-anim -accel on -gpu swiftshader_indirect &
    docker pull thyrlian/android-sdk-vnc
    docker run -d -p 5901:5901 -p 2222:22 -v $(pwd)/sdk:/opt/android-sdk thyrlian/android-sdk-vnc
    
    # Inside the container to setup emulator:
    echo "no" | avdmanager create avd -n test -k "system-images;android-25;google_apis;armeabi-v7a"
    emulator -avd test -no-audio -no-boot-anim -accel on -gpu swiftshader_indirect &
  10. Access the emulator from the host machine via ADB

    master

    You can connect to an emulator running inside a container from your host machine by exposing the ADB server port (5037).

    1. Start the container with port mapping:
      docker run -d -p 5037:5037 -p 2222:22 -v $(pwd)/sdk:/opt/android-sdk thyrlian/android-sdk-vnc
    
    2. **Connect from the host**:
       Before connecting, kill any local ADB server to ensure your client talks to the container's server:
       ```bash
    adb kill-server
    adb connect <container_ip_address>:5037
    adb devices
    adb kill-server
    adb connect <container_ip_address>:5037