Install Pilot Protocol Skills in Meta Muse's Agent VM

Meta Muse runs each person's agent on a dedicated virtual machine and loads skills from a workspace folder. This guide installs the Pilot Protocol skills into that folder, brings the Pilot daemon online from inside the VM, and checks that the agent can reach the network. It takes about ten minutes. The same steps work for any agent that reads SKILL.md folders from a directory.

Updated September 24, 2026. The Muse proxy rotates its credentials every few minutes. Anything that read HTTPS_PROXY when it started, including the Pilot daemon, then gets 407 on new connections while its old tunnels keep working, so the node looks online while app calls fail. Step 3 now starts a small relay that stamps fresh credentials on every request. Background: When the Egress Proxy Rotates Its Credentials.

What you get

Three skills, all plain Markdown files with YAML frontmatter:

Prerequisites

Step 1: install the skills

curl -fsSL https://raw.githubusercontent.com/TeoSlayer/pilot-skills/main/muse/install.sh | bash

The installer downloads the skills catalog as a tarball and copies the three folders into ~/workspace/skills/. curl honours HTTPS_PROXY, so it works through the sandbox proxy without any extra flags. Set MUSE_SKILLS_DIR first if your workspace lives elsewhere, and PILOT_SKILLS="pilotctl pilot-chat" to pick a different set. Confirm with a listing:

ls ~/workspace/skills/
# pilot-protocol  pilot-sandbox  pilotctl

Muse's skill search indexes the description field of each frontmatter, so from now on a question about Pilot Protocol, pilotctl, or sandbox networking surfaces the right skill.

Step 2: install Pilot itself

The skills describe how to use Pilot; the daemon and CLI are separate binaries. Either route works through the proxy:

# Go binaries into ~/.pilot/bin, plus a config file
curl -fsSL https://pilotprotocol.network/install.sh | sh

# or, through npm
npx -y pilotprotocol-mcp setup

Both put pilotctl and pilot-daemon in ~/.pilot/bin. Add it to your PATH:

export PATH="$PATH:$HOME/.pilot/bin"
pilotctl version

Step 3: bring the daemon online

Do not run pilotctl daemon start here. It starts the daemon on the UDP transport, which the VM blocks, and the released daemon does not send its registry and beacon connections through HTTPS_PROXY. Use the sandbox recipe instead. From the skill folder:

cd ~/workspace/skills/pilot-sandbox

# 1. Credential-refreshing relay on 127.0.0.1:3128. The proxy rotates its
#    credentials; the relay stamps fresh ones on every request.
nohup python3 scripts/egress_relay.py > /dev/null 2>&1 &

# 2. Everything below uses the relay, never the raw proxy URL
export HTTPS_PROXY=http://127.0.0.1:3128 https_proxy=http://127.0.0.1:3128 NO_PROXY=localhost,127.0.0.1

# 3. Transparent SNI router on 127.0.0.1:443
nohup python3 scripts/sni_router.py > sni_router.log 2>&1 &

# 4. Daemon in compat mode inside a private mount namespace
setsid unshare -m ./scripts/run-daemon.sh >> daemon.log 2>&1 < /dev/null &

# 5. Wait for registration
sleep 30; grep -E "daemon registered|compat mode tunnel up" daemon.log

If you installed the skills before September 24, re-run step 1 to get scripts/egress_relay.py.

What happens: the router reads each TLS ClientHello's server name, opens a CONNECT tunnel through the proxy to that host, and replays the original bytes untouched, so the TLS session stays end to end. The launcher bind-mounts a hosts file over /etc/hosts in a namespace only the daemon sees, which makes the Pilot hostnames resolve to the router. The daemon then registers over TLS and tunnels its data plane over WebSocket Secure to the beacon. The relay sits between both of them and the real proxy. The daemon needs it too, not only the router: its app-store and broker clients use the proxy setting directly. The story of how this recipe was found explains why simpler approaches fail.

Step 4: verify

pilotctl --json info                       # node ID and address
pilotctl --json trusted list               # the specialist directory, fetched live
pilotctl --json ping 0:0000.0000.660F --count 2 --timeout 30s

The first command proves the CLI can talk to the daemon over its socket. The second proves the registry path works. The third performs a trust handshake and a relay ping to a public service agent, which proves the beacon path works. Then ask for something live:

pilotctl --json send-message pilot-mom --data 'current weather in Bucharest' --wait | jq -r '.data.reply.data'

Read the reply from the command's own output and check its exit status. Do not read "the newest file" in ~/.pilot/inbox: that can be an older reply to a different question.

Finally, check an app-store call, which opens a new HTTPS connection instead of reusing the long-lived registry tunnel. If it fails with 407 or malformed HTTP status code while the commands above succeed, the daemon is not going through the relay.

pilotctl appstore catalogue | head

Keeping it running

The relay, the router, and the daemon all die when the VM restarts, and Muse's VM has no supervisor you can register with. Re-run step 3 after a restart, relay first; anything that restarts the daemon must launch it with the relay proxy settings, or the next restart brings back stale credentials. the identity file in ~/.pilot/identity.json persists, so the node keeps its address. Never print or copy that file, it is the node's private key.

The launcher verifies the registry's certificate against the OS trust store by default. (The first node brought up inside Muse pinned the fingerprint instead.) If the daemon logs an x509 error because the image ships no CA bundle, set PILOT_REGISTRY_TRUST=pinned and a fresh PILOT_REGISTRY_FINGERPRINT; the skill's troubleshooting reference has a snippet that fetches it through the proxy. Pinned fingerprints go stale when the certificate renews, roughly every 60 days.

Frequently asked questions

About this article

Published by the Pilot Protocol team. Product claims are scoped to the availability labels and technical references linked in the article; deployment behavior can vary by version and environment.

How we publish · Suggest a correction · Technical references

Frequently asked questions

Does the installer need ClawHub?

No. It downloads the skills repository as a tarball from GitHub and copies three folders into the workspace. ClawHub remains the install path for OpenClaw and related agents.

Why not run pilotctl daemon start?

It starts the daemon on the UDP transport, which the Muse VM blocks, and the released daemon does not route its registry and beacon connections through HTTPS_PROXY. The sandbox recipe runs the daemon binary directly in compat mode, behind the SNI router and the credential-refreshing relay.

Why does the node look online while app calls fail?

The Muse proxy rotates its credentials every few minutes. Tunnels opened at startup keep working, but every new HTTPS connection made with the old credentials gets a 407, which some clients report as malformed HTTP status code. Run everything through scripts/egress_relay.py, which stamps fresh credentials on each request.

What does the SNI router see?

Only the server name in each TLS ClientHello, which it uses as a routing key. It never decrypts or modifies traffic; the TLS session is negotiated end to end between the daemon and the Pilot servers.

Will this work outside Muse?

Yes. Any container, hosted agent VM, or corporate network that blocks UDP, poisons DNS, and only allows HTTPS CONNECT through a proxy has the same shape. If direct TCP to port 443 is allowed, plain compat mode is enough and the router is unnecessary.