#!/system/bin/sh # ===================================================================== # alexa-tablet-debloat.sh - Version 1.0 (2026-10-20) # Debloat script for the Amazon Alexa Tablet 12 Pro (Alexa Tablet UI 16.1.10, Android 16) # https://minnallab.com/guides/alexa-tablet-12-pro-debloat/ | License: MIT | Use at your own risk # # The script runs directly on the tablet, so it works the same on # Windows, macOS and Linux. All you need is ADB, no root. # # Usage: # adb push alexa-tablet-debloat.sh /data/local/tmp/ # adb shell sh /data/local/tmp/alexa-tablet-debloat.sh --dry-run # adb shell sh /data/local/tmp/alexa-tablet-debloat.sh [options] # # Without options (safe for everyone): # - remove ads, recommendations, demo/store mode and SIM leftovers # - disable Amazon telemetry # # Options (can be combined freely): # --amazon-apps Prime Video, Music, Audible, Kindle, Shopping, Photos, # Appstore, Silk, Luna, Amazon Kids # --alexa remove Alexa completely and hide the Alexa icon in # the Fire launcher (only lasts until the next reboot) # --no-account account-bound Amazon features (only useful without # an Amazon account): profiles, purchase protection, # Whispersync, Universal Search # --google duplicate Google apps: Gmail, Drive, Photos, Calendar, # Google TV, YouTube Kids/Music, Meet # --a11y Google accessibility apps (TalkBack, Switch Access, # Voice Access) # --keyboard disable the Fire keyboard (only if another keyboard # is active) # --free-space delete updates of the removed system apps # (frees storage under /data) # --all = --amazon-apps --alexa --no-account --google # --dry-run only show what would happen, change nothing # --restore undo everything # --force also run on other devices (not recommended) # # Simply run it again after every system update: packages that are # already removed are skipped. # The Fire launcher is deliberately NOT touched, because the home # gesture does not work without it. # ===================================================================== # ---------- Package groups ---------- ADS="com.amazon.kindle.kso com.amazon.firespotlight com.amazon.hedwig com.amazon.dags.tableteducation com.amazon.wallpaper com.amazon.partnerbrowsercustomizations" DEMO="com.amazon.d3 com.amazon.cx_offline com.amazon.tablet.chameleon com.amazon.kindle.otter.oobe.forced.ota com.amazon.samplewifiapp com.amazon.csapp com.amazon.ods.kindleconnect" AOSP="com.android.egg com.android.traceur com.android.stk com.android.simappdialog" TELEMETRY="com.amazon.client.metrics com.amazon.metrics com.amazon.device.crashmanager com.amazon.device.logmanager com.amazon.diode com.amazon.vdropbox" AMAZON_APPS="com.amazon.avod com.amazon.mp3 com.audible.application.kindle com.amazon.kindle com.amazon.windowshop com.amazon.clouddrive.photos com.amazon.venezia com.amazon.cloud9 com.amazon.cloud9.kids com.amazon.spiderpork com.amazon.tahoe com.amazon.tahoe.grownups com.amazon.tahoe.platform com.amazon.fawkes" ALEXA="com.amazon.dee.app com.amazon.tablet.voiceassistant com.amazon.genai.edgeaiagent com.amazon.alexa.calendar.app" ACCOUNT="com.amazon.h2settingsfortablet com.amazon.tablet.junco com.amazon.device.sync.sdk.internal com.amazon.sharingservice.android.client.proxy com.amazon.tablet.voyager" GOOGLE="com.google.android.gm com.google.android.apps.docs com.google.android.apps.photos com.google.android.calendar com.google.android.videos com.google.android.apps.youtube.kids com.google.android.apps.youtube.music com.google.android.apps.tachyon com.google.android.gms.location.history com.google.android.feedback" A11Y="com.google.android.marvin.talkback com.google.android.accessibility.switchaccess com.google.android.apps.accessibility.voiceaccess" KEYBOARD="com.amazon.firekeyboard" LAUNCHER="com.amazon.firelauncher" EXPECTED_MODEL="ATSPWI" # ---------- Options ---------- DRY=0; FORCE=0; RESTORE=0 DO_APPS=0; DO_ALEXA=0; DO_ACCOUNT=0; DO_GOOGLE=0; DO_A11Y=0; DO_KB=0; DO_FREE=0 usage() { sed -n '2,43p' "$0" 2>/dev/null | sed 's/^#//' } for a in "$@"; do case "$a" in --dry-run) DRY=1 ;; --amazon-apps) DO_APPS=1 ;; --alexa) DO_ALEXA=1 ;; --no-account) DO_ACCOUNT=1 ;; --google) DO_GOOGLE=1 ;; --a11y) DO_A11Y=1 ;; --keyboard) DO_KB=1 ;; --free-space) DO_FREE=1 ;; --all) DO_APPS=1; DO_ALEXA=1; DO_ACCOUNT=1; DO_GOOGLE=1 ;; --restore) RESTORE=1 ;; --force) FORCE=1 ;; -h|--help) usage; exit 0 ;; *) echo "Unknown option: $a"; echo "Help: sh $0 --help"; exit 1 ;; esac done # ---------- Helpers ---------- N_DONE=0; N_SKIP=0; N_FAIL=0 # has : is "package:" exactly in the list? has() { printf '%s\n' "$1" | grep -qxF "package:$2"; } ok() { echo " [OK] $1"; N_DONE=$((N_DONE+1)); } skip() { echo " [--] $1"; N_SKIP=$((N_SKIP+1)); } fail() { echo " [ERROR] $1"; N_FAIL=$((N_FAIL+1)); } dry() { echo " [TEST] $1"; N_DONE=$((N_DONE+1)); } refresh_lists() { INSTALLED=$(pm list packages --user "$U" 2>/dev/null) KNOWN=$(pm list packages -u --user "$U" 2>/dev/null) } remove_group() { # $1 = heading, $2 = package list echo ""; echo "== $1" for p in $2; do if ! has "$KNOWN" "$p"; then skip "$p (not present on this device)"; continue; fi if ! has "$INSTALLED" "$p"; then skip "$p (already removed)"; continue; fi if [ "$DRY" = 1 ]; then dry "$p would be removed"; continue; fi out=$(pm uninstall -k --user "$U" "$p" 2>&1) case "$out" in *Success*) ok "$p removed" ;; *) fail "$p: $out" ;; esac done } disable_group() { # $1 = heading, $2 = package list, $3 = user IDs echo ""; echo "== $1" for u in $3; do dis=$(pm list packages -d --user "$u" 2>/dev/null) inst=$(pm list packages --user "$u" 2>/dev/null) for p in $2; do if ! has "$inst" "$p"; then skip "$p (user $u: not installed)"; continue; fi if has "$dis" "$p"; then skip "$p (user $u: already disabled)"; continue; fi if [ "$DRY" = 1 ]; then dry "$p would be disabled for user $u"; continue; fi out=$(pm disable-user --user "$u" "$p" 2>&1) case "$out" in *disabled*) ok "$p disabled (user $u)" ;; *) fail "$p (user $u): $out" ;; esac done done } # ---------- Pre-checks ---------- U=$(am get-current-user 2>/dev/null | tr -dc '0-9') [ -z "$U" ] && U=0 MODEL=$(getprop ro.product.model) BUILD=$(getprop ro.build.display.id) echo "Alexa Tablet Debloat 1.0" echo "Device: $MODEL | Build: $BUILD | active user: $U" [ "$DRY" = 1 ] && echo ">>> DRY RUN (--dry-run): nothing will be changed." if [ "$MODEL" != "$EXPECTED_MODEL" ] && [ "$FORCE" != 1 ]; then echo "" echo "Aborted: this script is meant for the Alexa Tablet 12 Pro ($EXPECTED_MODEL)." echo "Found '$MODEL'. Use --force to run it anyway (at your own risk)." exit 1 fi # In Headless System User Mode (user 0 without a UI), also disable # telemetry for user 0. USERS="$U" [ "$U" != 0 ] && USERS="$U 0" refresh_lists # ---------- Restore ---------- if [ "$RESTORE" = 1 ]; then echo ""; echo "== Restore (user $U)" for p in $ADS $DEMO $AOSP $AMAZON_APPS $ALEXA $ACCOUNT $GOOGLE $A11Y; do has "$KNOWN" "$p" || continue if has "$INSTALLED" "$p"; then continue; fi if [ "$DRY" = 1 ]; then dry "$p would be restored"; continue; fi out=$(cmd package install-existing --user "$U" "$p" 2>&1) case "$out" in *installed*|*Success*) ok "$p restored" ;; *) fail "$p: $out" ;; esac done echo ""; echo "== Re-enable disabled packages" for u in $USERS; do dis=$(pm list packages -d --user "$u" 2>/dev/null) for p in $TELEMETRY $KEYBOARD $LAUNCHER; do has "$dis" "$p" || continue if [ "$DRY" = 1 ]; then dry "$p would be enabled for user $u"; continue; fi out=$(pm enable --user "$u" "$p" 2>&1) case "$out" in *enabled*) ok "$p enabled (user $u)" ;; *) fail "$p (user $u): $out" ;; esac done done if [ "$(settings get --user "$U" secure alexa_app_in_foreground 2>/dev/null)" = "1" ]; then if [ "$DRY" = 1 ]; then dry "Alexa icon would be shown again" else settings delete --user "$U" secure alexa_app_in_foreground >/dev/null 2>&1 am force-stop "$LAUNCHER" >/dev/null 2>&1 ok "Alexa icon shown in the launcher again"; fi fi echo "" echo "Done: $N_DONE changed, $N_FAIL errors. Note: restored apps may be on the" echo "factory version and need to be updated through the store." exit 0 fi # ---------- Debloat ---------- remove_group "Ads and recommendations" "$ADS" remove_group "Demo, setup and support packages" "$DEMO" remove_group "Android leftovers (SIM toolkit, tracing, easter egg)" "$AOSP" [ "$DO_APPS" = 1 ] && remove_group "Amazon apps" "$AMAZON_APPS" [ "$DO_ALEXA" = 1 ] && remove_group "Alexa" "$ALEXA" [ "$DO_ACCOUNT" = 1 ] && remove_group "Account-bound Amazon features" "$ACCOUNT" [ "$DO_GOOGLE" = 1 ] && remove_group "Google apps" "$GOOGLE" [ "$DO_A11Y" = 1 ] && remove_group "Google accessibility apps" "$A11Y" disable_group "Disable Amazon telemetry" "$TELEMETRY" "$USERS" # Alexa icon in the Fire launcher: the launcher only hides it while it # believes Alexa is in the foreground (secure setting alexa_app_in_foreground). if [ "$DO_ALEXA" = 1 ]; then echo ""; echo "== Hide the Alexa icon in the Fire launcher" if [ "$(settings get --user "$U" secure alexa_app_in_foreground 2>/dev/null)" = "1" ]; then skip "already hidden" elif [ "$DRY" = 1 ]; then dry "alexa_app_in_foreground would be set to 1" else settings put --user "$U" secure alexa_app_in_foreground 1 am force-stop "$LAUNCHER" >/dev/null 2>&1 ok "Alexa icon hidden" echo " Note: Alexa Tablet UI resets this value on every reboot." echo " Permanent fix with MacroDroid: reboot -> wait 60 s -> set value." fi fi # Only disable the Fire keyboard if it is not the active keyboard. if [ "$DO_KB" = 1 ]; then ime=$(settings get --user "$U" secure default_input_method 2>/dev/null) case "$ime" in com.amazon.firekeyboard*|""|null) echo ""; echo "== Fire keyboard" fail "The Fire keyboard is still active. Install and select another keyboard (e.g. Gboard) first." ;; *) disable_group "Disable the Fire keyboard (active: ${ime%%/*})" "$KEYBOARD" "$U" ;; esac fi # Delete updates of the removed system apps (frees storage under /data). if [ "$DO_FREE" = 1 ]; then echo ""; echo "== Free up storage (delete updates of removed system apps)" refresh_lists FPATHS=$(pm list packages -f -u --user "$U" 2>/dev/null) for p in $ADS $DEMO $AOSP $AMAZON_APPS $ALEXA $ACCOUNT $GOOGLE $A11Y; do has "$KNOWN" "$p" || continue has "$INSTALLED" "$p" && continue # only for removed apps upd=0 for line in $(printf '%s\n' "$FPATHS" | grep -F "=$p"); do case "$line" in "package:/data/app/"*"=$p") upd=1 ;; esac done [ "$upd" = 1 ] || continue if [ "$DRY" = 1 ]; then dry "update of $p would be deleted"; continue; fi out=$(pm uninstall-system-updates "$p" 2>&1) case "$out" in *Success*) ok "update of $p deleted" ;; *) fail "$p: $out" ;; esac done fi echo "" echo "Done: $N_DONE changed, $N_SKIP skipped, $N_FAIL errors." [ "$DRY" = 1 ] && echo "This was a dry run. Run it without --dry-run to apply the changes." [ "$DRY" = 0 ] && [ "$N_DONE" -gt 0 ] && echo "Recommended: reboot the tablet (adb reboot)." exit 0