Automating Nightly Sideloading of Open-Source Android TV Packages

Updated 2026-10-28

Automated scripts for nightly sideloading of open-source Android TV packages

If you maintain an open-source Android TV channel—say a custom launcher, a set of utility apps, or a small firmware layer—you probably find yourself pushing updates to every supported device nightly. Manually running adb sideload, confirming the install on each remote, and rebooting into testing is tedious and error-prone. The goal here is straightforward: let a script do the work while you sleep.

The technique works best with open-source packages on Google TV: the device exposes adb over Wi-Fi, apps live on the same sandboxed filesystem, and the typical Android TV install flow is adb sideload --install-overwrite /sdcard/package.xml package.zip. Automation becomes a single cron-style entry point that packages the latest source release, pulls the OTA zip, and fires the sideload command.

What you need before you script

Before automation pays off, verify three things on your target hardware:

If any of those premises fails, the script should abort and alert you—not silently skip the update and pretend the device is current.

Building the nightly sideload script

Here is the core structure of a reliable script. It targets an open-source project like the one behind the CleanYourTV launcher, which packages the launcher shell and a set of default widgets:

#!/usr/bin/env bash
set -euo pipefail

TV_IP="${1:-192.168.1.50}"
SSH_USER="tvadmin"
REMOTE_PATH="/data/local/tmp/android-sideload"
LATEST_URL="https://example.com/releases/latest-package.zip"

install_sideload() {
  local z="$1"
  adb -s "$TV_IP" shell am init-install /data/local/tmp/am_init.shell || true
  adb -s "$TV_IP" -w shell am install -v "$z"
}

ping_health() {
  adb -s "$TV_IP" shell "echo 'HEALTH_OK' > /sdcard/health-test.json"
  sleep 5
  local result
  result=$(adb -s "$TV_IP" shell cat /sdcard/health-test.json)
  if [[ "$result" == *"launcher"* ]]; then
    echo "Health check passed."
  else
    echo "Install failed or incomplete." >&2
    exit 1
  fi
}

The script takes the TV IP as the first argument (or defaults to 192.168.1.50), downloads the latest zip from a known mirror, and pushes am install. The wrapper around am install uses --install-overwrite for a clean replacement of the previous version.

Trade-offs you have to accept

Automating sideloads trades convenience for control. Be aware of what you are giving up:

These costs are small compared to the time saved during a busy week of testing. A practical compromise is to run the script nightly on non-production units and weekly on production units.

A short list of tools and helpers

Where to go from here

The next logical step after nightly sideloading is a staged rollout: push the first build to a single TV, validate the smoke test, then add a second script that compares the health-test JSON output across the fleet and alerts on divergence. That pattern—automated installation plus automated verification—keeps open-source Android TV channels fresh without turning the TV into a daily chore.

The script itself is small, but the value is cumulative. Each nightly pass means your open-source package arrives on every supported device the same day you release it, instead of waiting for someone to remember to copy the zip onto a USB stick and plug it in at your desk.

Related reading: more Android TV notes

Read next