android-emulator-layer
| Version | 2026.174.0700 |
| Repo | superproject |
Compose selkies + android-sdk + appium into a booting Android 16 emulator.
Composite glue layer that turns the underlying selkies-desktop +
android-sdk + appium-server stack into a running Android 16 (API 36,
google_apis_playstore x86_64, pixel_9a) emulator. The Play Store image
ships Play Store + Google Play services (GMS) + Google Chrome
preinstalled. Ships two helper scripts (start-emulator, wait-for-display),
two supervisord services (emulator + adb-server), the AVD volume, and the
/dev/kvm device-passthrough declaration that round-trips through the OCI
label into the quadlet. CPU/RAM are auto-sized from the host at runtime
(start-emulator). Optional GOOGLE_ACCOUNT_EMAIL + GOOGLE_AAS_TOKEN secrets
feed the charly check adb install-app --source google-play path. The
helper scripts, the AVD home directory, and the booted device are all
directly observable, so the behaviour is verifiable end to end.
Services
Section titled “Services”emulatoradb-server
Acceptance plan
Section titled “Acceptance plan”This candy’s plan: — the runnable spec charly check executes against a live deployment. check: steps are idempotent probes; run: steps change state.
| Intent | Step |
|---|---|
run |
command=set -e USERNAME=“$(getent passwd 1000 | cut -d: -f1)” # Add user to BOTH the container’s kvm group (satisfies the emulator’s # naive /etc/group preflight check that prints “The KVM line in # /etc/group is: [kvm:x:36:user]”) AND the nobody group (gid 65534). # /dev/kvm inside a rootless container is owned by nobody:nobody # because the host’s kvm group (gid 990) maps through subgid to the # overflow gid 65534. supervisord’s setuid+initgroups drops the # supplementary groups crun-keep-groups provided at container start, # so user must be listed in /etc/group for both groups to retain # access across the setuid boundary. if getent group kvm >/dev/null 2>&1; then usermod -aG kvm “${USERNAME}” fi if getent group nobody >/dev/null 2>&1; then usermod -aG nobody “${USERNAME}” fi |
run |
copy=start-emulator |
run |
copy=wait-for-display |
run |
mkdir=${HOME}/.android |
run |
mkdir=${HOME}/.android/avd |
check |
the start-emulator launcher is installed and executable |
check |
the wait-for-display gate is installed and executable |
check |
the AVD home directory exists for the runtime user |
check |
the emulator supervisord service is running |
check |
the adb server port is reachable on the host |
check |
adb reports the device fully booted |
check |
the booted AVD reports Android version 16 |
check |
adb=devices |
check |
adb=getprop |
check |
adb=shell |
check |
adb=shell |
check |
adb=wait-ui-settled |
check |
adb=shell |
check |
adb=shell |
check |
adb=shell |
check |
adb=shell |
check |
adb=shell |
check |
adb=screencap |
check |
adb=shell |
check |
adb=shell |
check |
adb=shell |
check |
adb=shell |
check |
adb=shell |
check |
adb=install |
check |
adb=shell |
check |
adb=screencap |
check |
adb=uninstall |
check |
appium=session-create |
check |
appium=raw |
check |
appium=install-app |
check |
adb=shell |
check |
adb=shell |
check |
appium=app-is-installed |
check |
appium=app-activate |
check |
appium=app-start-activity |
check |
appium=send-keys |
check |
appium=get-text |
check |
appium=app-start-activity |
check |
appium=gesture-tap |
check |
appium=get-attribute |
check |
appium=app-start-activity |
check |
appium=gesture-tap |
check |
appium=get-attribute |
check |
appium=app-start-activity |
check |
appium=gesture-scroll |
check |
appium=find |
check |
appium=app-start-activity |
check |
appium=gesture-tap |
check |
appium=gesture-tap |
check |
appium=source |
check |
appium=app-start-activity |
check |
appium=get-text |
check |
appium=app-start-activity |
check |
appium=gesture-swipe |
check |
appium=get-text |
check |
appium=app-start-activity |
check |
appium=gesture-drag |
check |
appium=source |
check |
appium=app-start-activity |
check |
appium=device-contexts |
check |
appium=device-context |
check |
appium=source |
check |
appium=device-context |
check |
appium=app-start-activity |
check |
appium=gesture-tap |
check |
appium=device-notifications |
check |
appium=source |
check |
appium=key-press |
check |
appium=device-info |
check |
appium=app-current-package |
check |
appium=device-orientation |
check |
appium=execute |
check |
appium=raw |
check |
appium=screenshot |
check |
appium=session-delete |