Skip to main content
Glama
megamen32

NanoKVM PicoClaw MCP

by megamen32
README.md
# NanoKVM PicoClaw MCP

An unofficial, self-hosted MCP adapter for the PicoClaw service installed by
[NanoKVM](https://github.com/sipeed/NanoKVM). It does not contain NanoKVM
firmware and is not affiliated with Sipeed or TinyAGI.

The adapter proxies NanoKVM's native PicoClaw MCP handler instead of copying
its screenshot and HID action semantics into another implementation. It also
has explicit NanoKVM status, reboot, and macOS recovery-key tools.

## Security boundary

Keep NanoKVM on a private network. Do not expose this stdio server directly to
the Internet. If remote MCP access is needed, put an authenticated gateway
such as GPTAdmin in front of one private relay instance.

The gateway machine is the only system that should hold device credentials and
the SSH key. Other MCP clients should authenticate to that gateway, never to
the NanoKVM itself.

The adapter requires a pinned `known_hosts` file for every SSH operation. It
refuses unknown SSH host keys and disables agent/port forwarding.

## Install

```bash
python3 -m pip install nanokvm-picoclaw-mcp
```

Set device-specific values in a mode-600 environment file owned by the relay
service account. Do not put them in a repository or in command-line arguments.

```bash
export NANOKVM_URL='http://nanokvm.private.example'
export NANOKVM_USER='admin'
export NANOKVM_PASSWORD='set-in-a-secret-store'
export NANOKVM_SSH_HOST='nanokvm.private.example'
export NANOKVM_SSH_USER='root'
export NANOKVM_SSH_KEY='/secure/path/nanokvm_ed25519'
export NANOKVM_SSH_KNOWN_HOSTS='/secure/path/known_hosts_nanokvm'
nanokvm-picoclaw-mcp
```

The server exposes `nanokvm_status`, `nanokvm_reboot`,
`nanokvm_hold_recovery_keys`, `picoclaw_tools_list`, `picoclaw_tools_call`,
and `picoclaw_chat`. Treat reboot, recovery-key and dynamic PicoClaw calls as
operator-only capabilities; a public gateway should enforce its own explicit
authorization policy.

## Development

```bash
python3 -m pip install -e '.[test]'
pytest -q
```

All tests are offline and use fake HTTP, WebSocket, and SSH transports.