Skip to main content
Glama
README.md
<p align="center"><strong>Exo Control</strong></p>

<h1 align="center">Realtime PC eyes and hands for any AI agent</h1>

<p align="center">
  Any model · MCP · CLI · Python<br/>
  Compact. Leased. Honest.
</p>

<p align="center">
  <a href="LICENSE"><img alt="MIT license" src="https://img.shields.io/github/license/ImAvgErix/ExoControl?style=flat-square&color=111111" /></a>
  <a href="https://pypi.org/project/exo-control/"><img alt="PyPI" src="https://img.shields.io/pypi/v/exo-control?style=flat-square&color=111111" /></a>
  <a href="docs/HARNESS.md"><img alt="Any harness" src="https://img.shields.io/badge/harness-MCP%20%7C%20CLI%20%7C%20Python-79f2c0?style=flat-square" /></a>
</p>

<p align="center">
  <a href="#install"><strong>Install</strong></a>
  ·
  <a href="docs/HARNESS.md">Harness</a>
  ·
  <a href="SECURITY.md">Safety</a>
  ·
  <a href="https://github.com/ImAvgErix/ExoLauncher">Exo Launcher</a>
</p>

**Exo Control** is a Windows Python library that gives any AI eyes and hands on the desktop. Same ops over MCP, CLI, or Python. Not an app and not a Setup.exe — install with `pip`.

| How the AI talks | Entry |
|------------------|--------|
| **MCP** | `exo_exec` · `exo_screenshot` · `exo_help` |
| **CLI** | `exo-control exec` · `exo-control script` · `exo-control doctor` |
| **Python** | `from exo_control import ExoExecEngine` |

Works with [Exo Launcher](https://github.com/ImAvgErix/ExoLauncher) when it is installed. Not required.

## Install

```bash
pip install exo-control
exo-control doctor
```

Optional extras:

```bash
pip install "exo-control[browser]"   # Playwright CDP
playwright install chromium
pip install "exo-control[web]"       # Browser Use web expert (optional)
```

Pin: `pip install "exo-control==2.4.0"` or `pip install "git+https://github.com/ImAvgErix/ExoControl.git@v2.4.0"`.
State lives under `~/.exo/`. Legacy `~/.aether/` is migrated automatically.

## MCP

```json
{
  "mcpServers": {
    "exo-control": {
      "command": "python",
      "args": ["-m", "exo_control.slim_mcp_server"]
    }
  }
}
```

`aether_*` tools register only when `EXO_MCP_ALIASES=1`. Prefer `exo_*`.

Do not set `PYTHONPATH` at a second tree. `exo-control doctor` reports shadowing.

## Quick script

```bash
exo-control script examples/notepad.json
```

```python
from exo_control import ExoExecEngine

ExoExecEngine().execute({
    "steps": [
        {"op": "lease_acquire", "agent_id": "demo", "task": "notepad", "ttl_sec": 90},
        {"op": "launch", "app": "notepad"},
        {"op": "type", "text": "hello from Exo Control"},
        {"op": "verify", "text": "hello from Exo Control"},
    ],
    "finally": [
        {"op": "window_close", "title": "Notepad", "discard_unsaved": True},
        {"op": "lease_release"},
    ],
})
```

Failed steps do not attach screenshots unless `screenshot_on_fail: true`. Use `{"op":"last_error"}`. Harness install is in [docs/HARNESS.md](docs/HARNESS.md).

## What it can do

| Surface | Ops |
|---------|-----|
| **Desktop** | UIA click/type/fill, aimed wheel + `scroll_into_view` + hover, live eyes, lease, multi-monitor |
| **Browser** | CDP snapshot refs, DOM click/type, page `scrollBy` / `scrollIntoView` |
| **OS** | Allowrooted files, HKCU registry, processes/services, fuzzy launch |
| **Search** | Lease-free `search` (`provider=perplexity\|tavily\|exa\|ddg\|serper\|brave`) + `search_content` |
| **Cloud browser** | Browser Use `browser_use` / `browser_use_start` (`BROWSER_USE_API_KEY`) |
| **Web extract** | `scrape` (`provider=firecrawl\|jina`); `crawl` / `site_map`; Stagehand `browser_act`; Skyvern; AgentQL |
| **Docs / find** | `files_convert` (`engine=markitdown\|docling`), `files_find` (Everything or walk) |
| **Memory / history** | `memory_add` / `memory_search` (local or Mem0); `recall` (Screenpipe) |
| **Mail / calendar** | `mail_list` / `cal_next` / `drive_get` / `todo` / `onenote` / `teams` / `mail_send` (Graph or Composio) |
| **Desk extras** | `xlsx`, `git`, `gh_pr`, `volume`, `winget`, `recycle`, `eventlog`, `window_move`, `browser_network` / `pdf` / `tabs` |
| **Wave 2** | `rag` / `steel_start` / `slack` / `notion` / `linear` / `pwsh` / `docker` / `hash` / `whoami` / `disk` |
| **Waves 3–5** | Graph writes, CDP extras, `wiki`/`weather`/`hn`, Jira/Discord/Airtable, `zip`/`sqlite`/`tree`, `which`/`dns`/`lock_pc` |
| **Pilot** | Original layer: `goal` / `checkpoint` / `proof` / `changed` / `undo` / `skill_save` / `skill_run` / `heal` |
| **Ready** | Honest `ready` map — what works here vs Windows-native vs needs a key |
| **Windows natives** | Stock volume/lock/wifi/power/recycle/TTS/dialog/dark_mode/idle/ports/Defender (no extra pip) |
| **Live seat** | `session_open` holds the desk like remote access; `pointer` / `mouse` / `keypress` / `drive` are raw HID |

Key-gated rows fail closed; `{"op":"ready"}` is the map; `stt` is a stub.
| **Desktop** | UIA click/type/fill, right/double click, menu, copy/paste, aimed wheel + `scroll_into_view` + hover, live eyes, `find`, lease, multi-monitor, window move/resize/snap |
| **Browser** | CDP snapshot refs, DOM click/type, page scroll, tabs/back/extract; `web_task` for multi-step jobs |
| **OS** | Allowrooted files (+ hash/zip/watch/reveal), HKCU registry, processes/services, drives, `os_info`, audio/power/idle, wifi, recycle, winget, `ms-settings:` |
| **Session** | Persistent prefs, plan, checkpoint, recover |

`{"op":"help"}` lists the core ops. `detail=true` is the full catalog. `find` searches the last read. `pc` is the owner snapshot (volume, power, idle, wifi). `exo-control pc` from a shell.

## Safety

- One desktop lease; `lease_status` / `session_status` never return the token
- Destructive OS ops need `confirm=true` (agent assertion, not a human prompt) unless **Full-Trust** is on
- Files stay in `EXO_FILE_ROOTS` unless the operator sets `EXO_ALLOW_OUTSIDE_ROOTS=1` (Full-Trust widens *user-profile* roots only)
- Hard denies in **default/trusted**: anti-cheat, unnamed PID kill, critical services, HKLM write, Windows/System32 writes, non-loopback CDP
- **Full-Trust owner mode** lifts those denials and auto-elevates privileged ops through a broker (MCP stays medium IL). First admin op may UAC once.
- Human kill-switch: create `~/.exo/KILL` or `exo-control trust kill` — agents cannot disarm it

- [SECURITY.md](SECURITY.md)

### Full-Trust (“this is my PC”)

Default install stays safe. Full-Trust is explicit and reversible:

1. `exo-control trust enable --ack "I own this PC"` (one-time human ack + audit log)
2. Set `EXO_TRUST=full` (or `EXO_FULL_TRUST=1`) on the MCP/CLI process and restart it
3. `exo-control trust status` should show `"level": "full"`

While Full-Trust is on, confirms are optional, the disk is in play, and privileged OS ops (HKLM, Program Files, services, anti-cheat) go through an elevated broker. The desktop MCP stays unelevated so clicks still work. One UAC to install the broker; after that it starts with the logon task.

    exo-control elevate status
    exo-control elevate install

Create `~/.exo/KILL` to freeze hands immediately. That file is the only remaining agent-proof stop.

## Docs

| Doc | Role |
|-----|------|
| [docs/HARNESS.md](docs/HARNESS.md) | Host install matrix |
| [docs/LIVE-MODEL.md](docs/LIVE-MODEL.md) | Lease / eyes / hands |
| [docs/CAPABILITY.md](docs/CAPABILITY.md) | Capability bar || [docs/API-STABILITY.md](docs/API-STABILITY.md) | 2.x public surface |
| [CHANGELOG.md](CHANGELOG.md) | Version history |

## License

MIT