Skip to main content

Documentation Index

Fetch the complete documentation index at: https://docs.usenightowl.com/llms.txt

Use this file to discover all available pages before exploring further.

NightOwl ships two remote MCP servers so AI coding assistants can drive the full dashboard — browse telemetry, triage issues, provision apps, manage teams, configure alert channels. Every AI-initiated change is logged with actor_type=mcp, so human and AI edits stay visually distinct and a token can be revoked instantly.

1. Generate a personal access token

Sign in to the dashboard, open Account → MCP Tokens, and create a token with a memorable label (e.g. “Laptop — Claude Code”). The raw token is shown once — copy it immediately; only the label, creation date, and last-used timestamp are visible afterwards. Revoking a token blocks every client using it instantly. Tokens are user-scoped, inherit your team membership, and carry the mcp ability — they only work against the MCP endpoints.

2. The two servers

NightOwl exposes two MCP endpoints. You’ll usually register both.
ServerEndpointScopeTypical use
Platform/mcp/platformYour account + every team you belong toProvisioning apps, inviting teammates, rotating agent tokens, inspecting agent health
Tenant/mcp/<app-id>A single connected app’s telemetryTriage issues, browse requests / exceptions / queries / jobs / logs, configure alert channels, manage data retention
The platform server has 25 tools; the tenant server has 53. Full coverage of the dashboard’s CRUD surface.

3. Connect your client

Claude Code

Register both servers:
claude mcp add --transport http nightowl-platform \
  https://api.usenightowl.com/mcp/platform \
  --header "Authorization: Bearer <token>"

claude mcp add --transport http nightowl \
  https://api.usenightowl.com/mcp/<app-id> \
  --header "Authorization: Bearer <token>"
Run /mcp in Claude Code to verify both servers connected.

Codex

Codex reads MCP servers from ~/.codex/config.toml and resolves the bearer token from an environment variable. Edit the config:
[mcp_servers.nightowl-platform]
url = "https://api.usenightowl.com/mcp/platform"
bearer_token_env_var = "NIGHTOWL_MCP_TOKEN"

[mcp_servers.nightowl]
url = "https://api.usenightowl.com/mcp/<app-id>"
bearer_token_env_var = "NIGHTOWL_MCP_TOKEN"
Then export the token in your shell profile (~/.zshrc, ~/.bashrc, etc.):
export NIGHTOWL_MCP_TOKEN="<token>"
Reload the shell (source ~/.zshrc) so Codex picks up the variable. Both servers can share the same env var, or use distinct ones if you’d rather scope tokens per server. If you’d rather not edit config.toml by hand, the same registration works via the CLI (token must already be exported):
codex mcp add nightowl-platform \
  --url https://api.usenightowl.com/mcp/platform \
  --bearer-token-env-var NIGHTOWL_MCP_TOKEN

codex mcp add nightowl \
  --url https://api.usenightowl.com/mcp/<app-id> \
  --bearer-token-env-var NIGHTOWL_MCP_TOKEN

Cursor

Cursor speaks bearer-token HTTP MCP natively. Add to .cursor/mcp.json (project-scoped) or ~/.cursor/mcp.json (global):
{
  "mcpServers": {
    "nightowl-platform": {
      "url": "https://api.usenightowl.com/mcp/platform",
      "headers": {
        "Authorization": "Bearer ${env:NIGHTOWL_MCP_TOKEN}"
      }
    },
    "nightowl": {
      "url": "https://api.usenightowl.com/mcp/<app-id>",
      "headers": {
        "Authorization": "Bearer ${env:NIGHTOWL_MCP_TOKEN}"
      }
    }
  }
}
The ${env:NIGHTOWL_MCP_TOKEN} reference keeps the raw token out of the file — export it from your shell profile. Cursor reloads the file when you save it.

Windsurf, Zed, and other stdio-only clients (via mcp-remote)

For clients that don’t yet support remote HTTP MCP, the mcp-remote shim proxies a remote server as stdio:
{
  "mcpServers": {
    "nightowl": {
      "command": "npx",
      "args": [
        "mcp-remote",
        "https://api.usenightowl.com/mcp/<app-id>",
        "--header",
        "Authorization: Bearer <token>"
      ]
    }
  }
}
Self-hosted NightOwl? Replace https://api.usenightowl.com with your own API URL. The paths are identical.

4. What’s available

Platform server (/mcp/platform)

CategoryTools
Appslist_apps, get_app, create_app, update_app, delete_app ⚠, test_app_connection, regenerate_app_token
Agent healthapp_health, app_health_history, app_health_diagnoses
Teamslist_teams, get_team, create_team, update_team, leave_team, update_team_member, remove_team_member
Invitationslist_team_invitations, create_team_invitation, revoke_team_invitation, accept_team_invitation
MCP tokenslist_mcp_tokens, create_mcp_token, delete_mcp_token
Subscriptionshow_subscription (read only — billing mutations use the dashboard)

Tenant server (/mcp/<app-id>)

CategoryTools
Overviewdashboard_overview
Issueslist_issues, get_issue, get_stack_trace, get_issue_occurrences, update_issue_status, bulk_update_issues, add_issue_comment
Telemetrylist_requests/get_request/get_route_detail, list_exceptions/get_exception, list_queries/get_query, list_jobs/get_job/get_job_attempt, list_commands/get_command/get_command_attempt, list_scheduled_tasks/get_scheduled_task/get_scheduled_task_attempt, list_cache_events, list_logs/get_log, list_mail/get_mail, list_notifications/get_notification, list_outgoing_requests/get_outgoing_request, list_users/get_user
Alertslist_alerts, mark_alert_read, mark_all_alerts_read
Alert channelslist_alert_channels, create_alert_channel, update_alert_channel, delete_alert_channel, toggle_alert_channel, test_alert_channel
Settingsget_settings, update_settings, list_environments, list_thresholds, update_thresholds, list_threshold_targets
Data managementfilter_options, preview_deletion, destroy_data
⚠ = destructive. These tools require an explicit confirm: "YES" argument and cannot be invoked accidentally.

5. Safety model

Scoped tokens

Tokens can only access apps where the owning user is a team member. The URL’s app-id is validated on every call.

Audit trail

Every mutating call writes an activity record with actor_type=mcp and actor_meta carrying the token label and client user-agent.

Instant revoke

Deleting a token from Account → MCP Tokens blocks every client using it — no redeploy, no restart.

Confirmation gates

Destructive tools (delete_app, regenerate_app_token, destroy_data) refuse to execute without confirm: "YES". Dry-run counterparts (preview_deletion) are always safe.

Webhook parity

Status changes made via MCP fire the same Slack, Discord, email, and webhook channels that a human edit would.

Self-revoke protection

delete_mcp_token refuses to delete the token currently making the call. Revoke it from the dashboard instead.

6. Example workflows

Once both servers are connected, a single prompt can span NightOwl data, your codebase, and team operations:
> What are the top three open exceptions in production,
  and is any of them caused by code I changed in the last week?
The assistant calls list_issues on the tenant server, then get_issue on each hit, then runs git log locally to cross-reference authorship — root cause in one turn. Close the loop:
> Mark issues #4812 and #4815 as resolved — both were fixed by
  the null check I just merged in OrderService.
A single bulk_update_issues call flips both statuses, writes activity rows, and fires the configured alert channels — attributed to MCP rather than to you directly. Provision a new environment:
> Create a staging app in the Acme team, test the DB connection,
  and give me the agent token so I can add it to Render's env vars.
Two platform calls (test_app_connection, create_app) — the agent token comes back once in the response. Retention cleanup:
> How much data would I free up by deleting requests older than
  90 days from the /api/legacy/* routes?
preview_deletion returns per-table row counts. Claude reads them, summarizes, and only invokes destroy_data (with confirm: "YES") after you approve.

Troubleshooting

Most common cause: a stale or mistyped token. Regenerate it in the dashboard and re-add the MCP server. Some clients cache server metadata — remove and re-add the server entry to force a refresh.
The app-id in the URL must match an app your user account has team access to. Copy the ID directly from the Apps page — it’s the last segment of the app detail URL.
Destructive tools require confirm: "YES" (exact string, uppercase, no punctuation). This is deliberate — it prevents a misinterpreted prompt from wiping an app.
Tools flush the app cache, so the dashboard refreshes within its normal polling interval (30s for list pages, 10s for dashboards). If it lingers longer, hard-refresh the browser tab.
The timeline supports filtering by actor_type. MCP-authored actions share the timeline with human ones and are only hidden if the filter excludes them.