# Hermes MCP Self Heal

> Use when Hermes MCP servers show failed or disconnected behavior and need structured self-heal: test each server, verify the backing listener or command, repair launchd persistence, and retest from Hermes.

- Skill: `undermybelt/hermes-mcp-self-heal` (Agent Skill)
- Install (CLI): `npx skillmds@latest add undermybelt/hermes-mcp-self-heal`
- Raw SKILL.md: https://api.skillmd.com/api/skills/undermybelt/hermes-mcp-self-heal/raw
- Safety review: pending
- Works with: Claude Code, Claude.ai, OpenAI Codex
- Category: AI & ML
- License: MIT
- Author: undermybelt (https://skillmd.com/u/undermybelt)
- Updated: 2026-09-17
- Page: https://skillmd.com/skills/undermybelt/hermes-mcp-self-heal

---


# Hermes MCP Self-Heal

## Overview

Use this when Hermes shows an MCP server as failed, disconnected, or unusable.
Goal: repair the backing service first, then prove Hermes can connect again.

Default environment assumed here:
- macOS
- Hermes config at `~/.hermes/config.yaml`
- MCP services may be stdio, HTTP, or launchd-backed local daemons

## When to Use

Trigger on asks like:
- `mcp failed`
- `mcp 挂了`
- `mcp 连不上`
- `修 mcp`
- `mcp 自愈`
- `openchronicle failed`
- `anything-analyzer failed`
- `browser-relay failed`
- `badboy-browser failed`
- `open-computer-use failed`
- `launchctl`
- `LaunchAgent`
- `后台常驻`
- `开机自启`

Load companion skills when relevant:
- `autonomous-ai-agents/hermes-agent` for Hermes config/CLI truth
- `software-development/systmt-dbggng` for structured root-cause flow
- `devops/anything-analyzer-mcp` for AA/headless/MITM specifics
- `devops/badboy-br-aa-routing` for real-Chrome/CDP/browser routing

## Core Rule

Do not patch Hermes config first.
First prove whether the backing service, listener, or executable is actually down.

When the user's goal is deliberate teardown/minimization rather than repair, switch modes explicitly:
- inspect the current `mcp_servers:` block and active launchd jobs first
- disable unwanted servers in `~/.hermes/config.yaml`
- stop the backing daemons and boot out matching LaunchAgents
- verify the remaining enabled set with `hermes mcp list`
- only then chase residual processes that should no longer exist

## Self-Heal Order

1. List configured MCP servers.
2. Test each failed server directly from Hermes.
3. Inspect the exact backend:
   - HTTP server -> listener/health endpoint
   - stdio command -> binary path/help/test
   - launchd-backed service -> plist, logs, launchctl state
4. Repair the backend service.
5. Retest from Hermes.
6. If the service must survive reboot/login, add or patch a per-user LaunchAgent.

## Minimal Command Set

### 1. Enumerate and test
```bash
hermes mcp list
hermes mcp test <name>
```

### 2. Inspect Hermes config slice
Read `~/.hermes/config.yaml` around `mcp_servers:` and confirm:
- `url` or `command`
- `args`
- `env`
- `headers`
- `timeout` / `connect_timeout`

### 3. HTTP MCP checks
```bash
lsof -nP -iTCP:<port> -sTCP:LISTEN || true
curl -sS -D - -o /dev/null -H 'Accept: application/json, text/event-stream' http://127.0.0.1:<port>/mcp || true
```

### 4. stdio MCP checks
```bash
ls -l <binary>
<binary> --help
hermes mcp test <name>
```

### 5. launchd checks
```bash
launchctl print gui/$(id -u)/<label> | sed -n '1,140p'
tail -n 80 <stdout-log> 2>/dev/null || true
tail -n 80 <stderr-log> 2>/dev/null || true
```

### 6. launchd reload
```bash
launchctl bootout gui/$(id -u) "$HOME/Library/LaunchAgents/<label>.plist" >/dev/null 2>&1 || true
launchctl bootstrap gui/$(id -u) "$HOME/Library/LaunchAgents/<label>.plist"
launchctl kickstart -k gui/$(id -u)/<label>
```

## Known Local Truths

### OpenChronicle
- Hermes URL: `http://127.0.0.1:8742/mcp`
- Local binary: `~/.local/bin/openchronicle`
- Persistence plist: `~/Library/LaunchAgents/com.thrill3r.openchronicle.plist`
- If failed, first run:
```bash
openchronicle status
openchronicle start
hermes mcp test openchronicle
```
- Root cause already seen live: daemon stopped -> no listener on 8742.

### anything-analyzer
- Hermes URL: `http://localhost:23816/mcp`
- Persistence plist: `~/Library/LaunchAgents/com.anything-analyzer.dev.plist`
- Must keep headless/no-UI unless user explicitly asks otherwise.
- Check 23816 listener before touching config.

### browser-relay
- Backing LaunchAgent: `~/Library/LaunchAgents/com.liaotechs.browser-relay.plist`
- Typical listener: `127.0.0.1:18795`
- Hermes side is stdio wrapper; verify both listener and `hermes mcp test browser-relay`.

### badboy-browser
- Hermes side uses shell wrapper + env injection.
- Transport may pass even when runtime emits harmless asyncio shutdown noise.
- Success criterion is `hermes mcp test badboy-browser` discovering tools, not zero stderr noise.

### open-computer-use
- Usually stdio only.
- Verify executable path first; then `hermes mcp test open-computer-use`.

## LaunchAgent Pattern

For durable local MCP services on macOS, prefer per-user LaunchAgents:
- file under `~/Library/LaunchAgents/`
- `RunAtLoad`
- `KeepAlive`
- explicit `PATH`
- explicit logs under `~/Library/Logs/`

Use listener guards if the underlying CLI exits non-zero when already running.
Observed example: `openchronicle start` returns exit code 1 when daemon already exists, so a guard like `lsof ... || start` prevents launchd restart churn.

## Verification Checklist

- [ ] `hermes mcp list` shows target enabled
- [ ] `hermes mcp test <name>` succeeds after repair
- [ ] backing listener or stdio binary was directly verified
- [ ] if launchd-backed, plist path and `launchctl print` were checked
- [ ] if persistent service needed, LaunchAgent exists and reload command works
- [ ] final result proven from Hermes side, not only backend side

## Common Pitfalls

1. Patching `~/.hermes/config.yaml` before checking whether the backend daemon is simply down.
2. Missing the teardown case: if the user wants MCPs gone, leaving `enabled: true` on `hermes`, `browser-relay`, `badboy-browser`, `anything-analyzer`, or `openchronicle` guarantees they can come back after reload/restart.
3. Treating noisy stderr as failure when `hermes mcp test` already proves tool discovery works.
4. Forgetting `Accept: application/json, text/event-stream` on HTTP MCP probes.
5. Using ad-hoc shell backgrounding instead of launchd for services meant to persist.
6. For AA tasks, accidentally opening UI/Electron despite user preference for hidden/headless mode.
7. Declaring success because a port listens, without retesting from Hermes.
8. Killing child MCP processes without checking the parent chain; a surviving parent `hermes mcp serve` can recursively respawn `browser-relay-mcp-line`, `hermes_context_server.py`, and more `hermes mcp serve` children.

