agentdev
Provides tools for controlling and inspecting an Android phone through the ADB protocol (speaking directly to an adb server, no adb binary required): run shell commands, stream and filter logcat (including crash/ANR detection), dump and search the accessibility UI tree, tap/swipe/text input, take screenshots, list/start/stop/install/clear apps, send intents and open URLs, read and write device settings, and pull/push files.
This server does not currently have a deployable release on Glama. Follow the repository's setup instructions to install and configure it for your MCP client, including any required credentials and local dependencies.
agentdev — Android device tools for AI agents (Termux + proot)
A zero-dependency toolkit that gives an AI agent hands on an Android phone: run adb
commands, read logcat, dump and drive the UI, install APKs, pull files, grab screenshots.
Designed for the setup where it's actually painful: an agent running inside a proot
distro on Termux, where a normal adb binary may not exist and a USB device is never
available. agentdev ships its own implementation of the ADB wire protocol, so it
talks straight to the adb server running on your Termux host — no binary, no pip
install, pure Python stdlib (3.8+).
┌──────────── proot distro (where the agent lives) ─────────────┐
│ agent ──► agentdev ──TCP 127.0.0.1:5037──► adb server │
│ (socket backend, no adb binary needed) │
└───────────────────────────────────────────────────────────────┘
Termux host ▲ adb binary + wireless debugging
│ USB or TCP
📱 phoneThree ways to call it, same 41 tools underneath:
Interface | Use it for |
MCP server ( | Claude Desktop, Cline, Continue, any MCP client |
CLI ( | shell-capable agents, scripts, cron |
Python / tool schemas | OpenAI, Anthropic, Gemini function calling (schemas exported for you) |
Quick start
# 1. On the Termux HOST
pkg install python android-tools proot-distro
adb start-server
# 2. Get the toolkit into the distro
proot-distro login debian
# (copy this directory in, or git clone it)
# 3. Verify end to end
export ADB_SERVER_SOCKET=tcp:127.0.0.1:5037
python3 -m agentdev doctordoctor tells you exactly which link in the chain is broken — backend, server, device
authorisation, or missing on-device binaries.
Then:
python3 -m agentdev device_info # model, Android version, screen, root
python3 -m agentdev shell_exec --command "pm list packages -3" --allow-dangerous
python3 -m agentdev logcat_crashes --package com.example.app
python3 -m agentdev ui_dump --max-nodes 40
python3 -m agentdev tap_text --text "Sign in"
python3 -m agentdev screenshot --name home
python3 -m agentdev mcp # serve to an MCP clientNo install step required — python3 -m agentdev works from the repo. Optional:
pip install -e . puts an agentdev command on PATH.
Connecting the phone (wireless debugging)
# on the phone: Developer options → Wireless debugging → Pair device with pairing code
adb pair 192.168.1.5:37123 # enter the 6-digit code
adb connect 192.168.1.5:5555
adb devices -l # must say "device", not "unauthorized"The phone only needs to reach the host's adb server; the proot distro never touches the phone directly.
Related MCP server: scrcpy-mcp
The 41 tools
Diagnostics — doctor, device_list, device_select, device_wait, adb_connect,
device_info, battery, net_info, device_unlock
Shell & files — shell_exec, file_ls, file_read, file_pull, file_push,
file_delete*
Logs — logcat_dump (bounded snapshot, level / tag / pid / keyword filters),
logcat_watch (live window — trigger an action, then watch what it logs),
logcat_crashes (Java exceptions, ANRs, native aborts, Force finishing activity)
UI & input — ui_dump (accessibility tree with tap centres), ui_find, ui_wait
(poll until an element appears/disappears), scroll_to (swipe until visible),
tap, tap_text, swipe, long_press, input_text, key_event, screenshot,
screen_state
Apps & intents — app_start, app_stop, app_clear_data, app_current,
app_list, package_info, app_install, open_url, intent_send
Settings — settings_get, settings_set*
* = gated behind --allow-dangerous / AGENTDEV_ALLOW_DANGEROUS=1.
Every tool returns JSON. Failures come back as
{"error": "...", "kind": "adb|timeout|internal", "retryable": bool, "hint": "..."}
instead of raising, so one bad call never kills the agent loop — and the hint tells the
agent what to do next (accept the RSA prompt, reconnect the transport, wake the screen…).
Wiring it into an agent
MCP (Claude Desktop, Cline, Continue…)
{
"mcpServers": {
"android": {
"command": "python3",
"args": ["-m", "agentdev", "mcp"],
"env": {
"AGENTDEV_ALLOW_DANGEROUS": "1",
"ADB_SERVER_SOCKET": "tcp:127.0.0.1:5037"
}
}
}
}See examples/claude_desktop_config.json. Smoke-test without a chatbot:
python3 examples/mcp_client.py device_list
OpenAI-compatible function calling
export OPENAI_API_KEY=sk-...
python3 examples/openai_agent.py "Open Settings, enable Airplane mode, then show me the log"Works with local models too — point OPENAI_BASE_URL at Ollama / LM Studio / vLLM.
Anthropic tool use
export ANTHROPIC_API_KEY=sk-ant-...
python3 examples/anthropic_agent.py "What app is in the foreground?"Any custom agent
python3 -m agentdev schema --format openai > tools.openai.json
python3 -m agentdev schema --format anthropic > tools.anthropic.json
python3 -m agentdev schema --format gemini > tools.gemini.jsonfrom agentdev.tools import Context, run_tool
ctx = Context() # one per agent session
run_tool("tap_text", {"text": "Sign in"}, ctx)
run_tool("logcat_dump", {"level": "E", "grep": "NullPointer", "limit": 50}, ctx)AGENTS.md has the operating playbook to paste into your system prompt.
Why agents don't get stuck
Long-tool-call agents fail on flaky transports, not on missing features. agentdev bakes in the recovery paths:
Error triage — every failure is classified (
agentdev/errors.py) into ahint+retryableflag:unauthorized→ "tap Allow on the phone";device offline→ "adb reconnect offline";uiautomator dump failed→ "wake the device, or use screenshot".Transient retry — a dropped socket / stale transport is retried once automatically after resetting the session, so a server restart doesn't burn a turn.
Hierarchy cache — repeated
ui_find/ui_wait/tap_textcalls within 1.5 s reuse one uiautomator dump (AGENTDEV_UI_TTL); every mutating tool invalidates it.Wait, don't sleep —
ui_waitanddevice_waitreplace blindsleeps, so slow devices cost latency instead of correctness.Bounded everything — log output, stream windows, screenshots and file reads are all capped, so a chatty device can't blow the model's context window.
Secret hygiene —
scripts/check_secrets.py(run in CI) blocks any commit containing GitHub/AWS/OpenAI/Anthropic tokens or private keys.
Configuration
Env var | Default | Meaning |
|
| where the adb server listens |
|
| adb server port |
| first online device | target serial |
|
| unlock |
|
| seconds per shell call |
|
| chars returned to the model per call |
|
| where screenshots / pulled files land |
|
| on-device scratch dir |
|
| seconds the hierarchy cache stays valid |
| auto | explicit path to an adb binary (binary backend) |
CLI flags --allow-dangerous --serial --adb-host --adb-port --backend --raw work before
or after the subcommand.
How the two backends work
socket (default, recommended) — speaks the adb protocol directly: %04x-framed
requests, OKAY/FAIL status words, host:devices-l, host:transport:<serial> +
shell:<cmd>. Works inside proot with no adb binary and no privileged mounts. Exit
codes are recovered by appending a marker echo to each command (the adb shell service
doesn't propagate them over the wire). Files move as base64 chunks over the shell channel,
so sync: services and adb push aren't needed.
binary (fallback) — shells out to adb from PATH (or
/data/data/com.termux/files/usr/bin/adb, or ADB_BIN), and drives adb push/adb install
when available. Auto-detected if the server probe fails; force with --backend binary.
Long-lived streams (logcat) reuse one socket via iter_stream, with per-read timeouts so
a silent device can never wedge the agent.
Notes for proot
The distro normally shares the host network namespace, so
127.0.0.1:5037reaches the Termux adb server. If it doesn't, use the host's Wi-Fi IP:AGENTDEV_ADB_HOST=192.168.1.10. (Binding a server inside proot to a port the host can see does not work — run it on the host.)Termux's adb binary can't be executed inside some rootfs images (glibc vs bionic), which is exactly why the socket backend exists.
No root required on the phone; everything here runs through the normal adb shell user. Root-only commands just fail with a clear error.
Safety
Destructive tools are gated; leave
AGENTDEV_ALLOW_DANGEROUSunset for read-only agents.screenshot/file_pullwrite intoAGENTDEV_WORKDIR— never into system paths.Every device action is logged to stderr by the MCP server, stdout stays protocol-clean.
shell_execruns as the adb shell user: it cannot silently escalate.
Tests
python3 -m unittest discover -s tests -v # 62 tests, no phone needed
python3 scripts/check_secrets.py --all # credential scan (also runs in CI)
make test lint secrets # same thing via Makefiletests/fake_adb.py is a real adb-protocol server that executes commands on the local
machine (and serves canned uiautomator/wm/settings/screencap payloads), so the
socket backend, framing, exit codes, file transfer, UI hierarchy parsing, tap-coordinate
math, screenshot decoding, cache invalidation, retry logic, tool registry, MCP handshake
and CLI are all exercised without hardware. Point it at a real phone any time
with python3 tests/fake_adb.py 5038 (do not run it on 5037 next to a real server).
Limitations
input_textis ASCII-only (an Androidinputlimitation); useshell_execwith a clipboard helper for Unicode.ui_dumpusesuiautomator— not available on games/Flutter canvases with no accessibility nodes; fall back toscreenshot+tap.Pushing files over base64 is fine for MBs, slower than
adb pushfor large APKs (the binary backend usesadb pushautomatically when present).
MIT licensed.
This server cannot be deployed
Maintenance
Related MCP Connectors
Give your AI agent a real cloud Android phone: push APKs, drive it, get screenshots and logs.
Let AI agents control Android and iOS devices on Mobilerun Cloud: screen, input, apps, workflows.
Cloud Android phones for AI agents: create a phone, read the screen, tap, type, install APKs, park.
Cloud Android phones for AI agents: read the screen, tap, type, install APKs, park and resume.
Related MCP Servers
- AlicenseNot gradedqualityAmaintenanceEnables AI agents to see and control Android devices through ADB and screen mirroring, supporting screen capture, touch input, app management, UI element finding, file transfer, shell commands, clipboard access, and audio/video streaming.374 npmMIT
- AlicenseNot gradedqualityAmaintenanceEnables AI agents to see and control Android devices through ADB and scrcpy, supporting screen capture, taps, swipes, typing, app management, UI inspection, file transfer, shell commands, and audio/video streaming.374 npmMIT
- AlicenseNot gradedqualityAmaintenanceEnables AI agents to see and control Android devices through ADB and scrcpy, including screenshots, taps, swipes, typing, app management, UI inspection, file transfer, shell commands, audio/video streaming, and clipboard access.374 npmMIT
- AlicenseNot gradedqualityAmaintenanceEnables AI agents to see and control Android devices via ADB and scrcpy, supporting screenshots, taps, swipes, typing, app management, UI inspection, file transfer, shell commands, and audio/video streaming.374 npmMIT