# MCP server

daemonitor runs a Model Context Protocol server, so an AI agent such as Claude Code or Cursor can read your fleet directly. Ask it what is broken and it answers from the same data as the dashboard, with the server's reason for every problem.

The server is read-only. It sees exactly what the [external API](./api.md) sees for the key you give it.

## Connect

Create an API key under Settings, API Keys. Use an [organization-scoped key](./api.md#organization-scoped-keys) if the agent should only see one customer.

Claude Code:

```bash
claude mcp add --transport http daemonitor https://daemonitor.com/api/mcp --header "Authorization: Bearer <api key>"
```

Any client that takes a JSON config with headers, such as Cursor:

```json
{
  "mcpServers": {
    "daemonitor": {
      "url": "https://daemonitor.com/api/mcp",
      "headers": { "Authorization": "Bearer <api key>" }
    }
  }
}
```

The key also works as an `x-api-key` header. A missing, unknown or expired key fails when the client connects, with `401`.

Clients that only support OAuth for remote servers, such as custom connectors on claude.ai, can't connect yet.

## Tools

| Tool | What it returns |
|---|---|
| `fleet_status` | Totals by level, one line per system, and every service at `warn` or `crit` with the server's reason and its failing units. `system` narrows it to one system. `include_ok` adds the healthy services. |
| `get_system` | Every service on one system, by name or id, with its units (containers, devices, checks) and metrics. |
| `get_service_history` | Recent samples for one service, oldest first. CPU and memory for hosts, response time for web checks, requests for Cloudflare. `limit` defaults to 60 and stops at 240. |
| `list_incidents` | [Incidents](./incidents.md) marked client-visible, with their timelines. `open` and `since` filter them. |
| `list_groups` | Your groups with each member service's level, so a problem can be traced to the app it belongs to. |

`get_service_history` finds the service by id, by name, or by plugin type such as `os` or `docker` when only one service on the system has it. A name or type that matches several services returns each one's type and id instead of picking one. On a host with a web check and a compose project both called `shop`, pass the id.

Levels are `ok`, `warn`, `crit` and `standby`. `standby` means correctly idle, such as a [cluster](./clusters.md) member that isn't running a leader-only service. A service that stopped reporting is `crit` with an `OFFLINE` status.

## Limits

- Machine-raised alerts aren't a separate tool. `fleet_status` shows every current problem, which is what an alert is about.
- `list_incidents` returns only client-visible incidents, the same as the external API.
- Cluster rollup items aren't included, so a group made of them lists fewer members than the dashboard shows.
