Skip to content

REST API

MCP Hangar exposes a full REST API alongside the MCP protocol layer. The API is mounted at /api/ when running in HTTP mode and provides CRUD operations, real-time WebSocket streams, and operational endpoints.

Quick Start

Start Hangar in HTTP mode:

bash
mcp-hangar serve --http --port 8000

The REST API is available at http://localhost:8000/api/.

bash
# List all providers
curl http://localhost:8000/api/providers

# Get system info
curl http://localhost:8000/api/system

# Start a provider
curl -X POST http://localhost:8000/api/providers/math/start

Authentication

When authentication is enabled, pass your API key in the X-API-Key header:

bash
curl -H "X-API-Key: mcp_your_key_here" http://localhost:8000/api/providers

See the Authentication guide for setup instructions.

Endpoints Overview

All endpoints return JSON. Error responses follow the envelope format:

json
{
  "error": "ProviderNotFoundError",
  "message": "Provider 'unknown' not found",
  "status_code": 404
}

Providers

MethodPathDescription
GET/api/providersList all providers (optional ?state=ready filter)
POST/api/providersCreate a new provider
GET/api/providers/{id}Get provider details
PUT/api/providers/{id}Update provider configuration
DELETE/api/providers/{id}Delete a provider (stops it first)
POST/api/providers/{id}/startStart a provider
POST/api/providers/{id}/stopStop a provider
GET/api/providers/{id}/toolsList provider tools
GET/api/providers/{id}/healthGet health status
GET/api/providers/{id}/logsGet buffered log lines (?lines=100)
GET/api/providers/{id}/tools/historyTool invocation history

Groups

MethodPathDescription
GET/api/groupsList all provider groups
POST/api/groupsCreate a new group
GET/api/groups/{id}Get group details
PUT/api/groups/{id}Update group configuration
DELETE/api/groups/{id}Delete a group
POST/api/groups/{id}/rebalanceTrigger group rebalance
POST/api/groups/{id}/membersAdd a member to the group
DELETE/api/groups/{id}/members/{member_id}Remove a member

Discovery

MethodPathDescription
GET/api/discovery/sourcesList discovery sources
POST/api/discovery/sourcesRegister a new source
PUT/api/discovery/sources/{id}Update a source
DELETE/api/discovery/sources/{id}Remove a source
POST/api/discovery/sources/{id}/scanTrigger immediate scan
PUT/api/discovery/sources/{id}/enableEnable/disable a source
GET/api/discovery/pendingList providers pending approval
GET/api/discovery/quarantinedList quarantined providers
POST/api/discovery/approve/{name}Approve a pending provider
POST/api/discovery/reject/{name}Reject a pending provider

Catalog

MethodPathDescription
GET/api/catalogList catalog entries (?search=, ?tags=)
GET/api/catalog/{id}Get a catalog entry
POST/api/catalogAdd a custom catalog entry
DELETE/api/catalog/{id}Remove a catalog entry
POST/api/catalog/{id}/deployDeploy a catalog entry as a live provider

Configuration

MethodPathDescription
GET/api/configGet sanitized current configuration
POST/api/config/reloadTrigger hot-reload from disk
POST/api/config/exportExport current state as YAML
POST/api/config/backupCreate a rotating config backup
GET/api/config/diffDiff on-disk vs in-memory configuration

System

MethodPathDescription
GET/api/systemSystem info (uptime, version, metrics summary)

Auth Management

MethodPathDescription
POST/api/auth/keysCreate an API key
DELETE/api/auth/keys/{key_id}Revoke an API key
GET/api/auth/keys/{principal_id}List keys for a principal
GET/api/auth/rolesList all roles
GET/api/auth/roles/builtinList built-in roles
GET/api/auth/roles/{role_id}Get role details
POST/api/auth/rolesCreate a custom role
PUT/api/auth/roles/{role_id}Update a custom role
DELETE/api/auth/roles/{role_id}Delete a custom role
POST/api/auth/principals/{id}/rolesAssign a role to a principal
DELETE/api/auth/principals/{id}/roles/{role_id}Revoke a role
GET/api/auth/principalsList principals
GET/api/auth/principals/{id}/rolesList roles for a principal
POST/api/auth/check-permissionCheck if a principal has permission
GET/api/auth/policies/{provider}/{tool}Get tool access policy
PUT/api/auth/policies/{provider}/{tool}Set tool access policy
DELETE/api/auth/policies/{provider}/{tool}Clear tool access policy

Observability

MethodPathDescription
GET/api/observability/metricsPrometheus metrics + JSON summary
GET/api/observability/auditAudit log (?provider_id=, ?event_type=, ?limit=)
GET/api/observability/securitySecurity events
GET/api/observability/alertsAlert history (?level=)
GET/api/observability/metrics/historyTime-series metrics snapshots

Maintenance

MethodPathDescription
POST/api/maintenance/compactCompact an event stream

WebSockets

PathDescription
/api/ws/eventsReal-time domain event stream
/api/ws/stateProvider state change stream
/api/ws/providers/{id}/logsLive log stream for a provider

See the WebSockets guide for connection details.

Examples

Create a Provider

bash
curl -X POST http://localhost:8000/api/providers \
  -H "Content-Type: application/json" \
  -d '{
    "provider_id": "my-llm",
    "mode": "subprocess",
    "command": ["python", "-m", "llm_server"],
    "idle_ttl_s": 600,
    "description": "LLM inference provider"
  }'
json
{"provider_id": "my-llm", "created": true}

Create a Group with Members

bash
# Create group
curl -X POST http://localhost:8000/api/groups \
  -H "Content-Type: application/json" \
  -d '{
    "group_id": "llm-pool",
    "strategy": "round_robin",
    "min_healthy": 1
  }'

# Add members
curl -X POST http://localhost:8000/api/groups/llm-pool/members \
  -H "Content-Type: application/json" \
  -d '{"member_id": "my-llm", "weight": 1, "priority": 1}'

Export and Diff Configuration

bash
# Export current state
curl -X POST http://localhost:8000/api/config/export

# See what changed vs disk
curl http://localhost:8000/api/config/diff

Register a Discovery Source

bash
curl -X POST http://localhost:8000/api/discovery/sources \
  -H "Content-Type: application/json" \
  -d '{
    "source_type": "docker",
    "mode": "additive",
    "enabled": true,
    "config": {"socket_path": "/var/run/docker.sock"}
  }'

CORS

CORS is configured via environment variables:

VariableDefaultDescription
MCP_CORS_ORIGINS*Allowed origins (comma-separated)
MCP_CORS_METHODS*Allowed methods
MCP_CORS_HEADERS*Allowed headers

For production, restrict origins to your dashboard URL:

bash
export MCP_CORS_ORIGINS="https://dashboard.example.com"

Error Handling

All domain exceptions are mapped to HTTP status codes:

ExceptionStatus Code
ProviderNotFoundError404
ValidationError422
RateLimitExceeded429
CompactionError500
Other MCPError500

The error envelope always contains error (exception class name), message, and status_code.

Full Reference

For complete request/response schemas, see the REST API Reference.

Released under the MIT License.