Skip to content

MCP tool reference

The Starsystem server exposes 30 MCP tools over a stateless WebStandard Streamable HTTP transport, mounted at POST /mcp. These tools let AI agents build, control, and observe multi-service stacks without shell access.

Add to your MCP config (Claude Desktop / Claude Code):

{
"mcpServers": {
"starsystem": {
"command": "ss",
"args": ["server", "--port=7700"],
"type": "stdio"
}
}
}

Or connect to a running server:

{
"mcpServers": {
"starsystem": {
"url": "http://localhost:7700/mcp"
}
}
}

Read the full system snapshot. Call this first before making any changes.

Returns each service with its type, name, mode, runtime status, PID, URL, and phase flags (_tf, _ansible, _cicd).

{
"name": "my-app",
"services": [
{
"id": "postgres",
"service": { "type": "postgres", "name": "Postgres", "mode": "local" },
"runtime": { "status": "running", "pid": 1234, "url": "postgresql://localhost:5432/myapp" }
}
]
}

Status values: running | starting | stopped | error | external | unknown


Return the raw starsystem.yaml content. Read this before proposing modifications — edit precisely rather than rewriting the whole file.


Validate a proposed YAML string against the schema without applying it.

Inputs: yaml: string

Always call this before starsystem_apply_yaml.


Get the current runtime status of all services at once. Lighter than starsystem_read_system — returns only { id, status, pid?, url? } per service.


Get the status of a single service.

Inputs: service_id: string


Apply a complete starsystem.yaml to the running server. The server validates, writes, syncs the process manager, and broadcasts a reload event to the UI.

Inputs: yaml: string

Always call starsystem_validate_yaml first.


Add a single new service without rewriting the whole YAML. The service is validated, registered with the process manager, and health watching starts immediately.

Inputs: id: string, service: object

{
"id": "cache",
"service": {
"type": "redis",
"name": "Cache",
"local": { "command": "redis-server", "port": 6379 }
}
}

Merge-update a service’s definition. Use this to change a port, mode, or command without touching the rest of the config.

Inputs: id: string, patch: object


Stop a service, remove it from the YAML, and clean up all connections referencing it.

Inputs: id: string


Set visual canvas positions for one or more nodes. No service state changes.

Inputs: positions: Record<string, { x: number, y: number }>

Lay out the graph meaningfully before handing off to the user — data layer at bottom, API in the middle, clients at top.


Switch a service between local, cloud, or auto mode.

Inputs: id: string, mode: "local" | "cloud" | "auto"

When switching to cloud, missing credentials are caught first:

{ "ok": false, "needsCredentials": true, "missing": ["DATABASE_URL"] }

Call starsystem_credentials_status to surface what the user needs to provide, then retry.


Start a service and its depends_on dependencies in order.

Inputs: id: string, wait_for_healthy?: boolean (default true), timeout_sec?: number

When wait_for_healthy is true, the call blocks until the process is running or the timeout expires. On failure, the response includes the last 30 log lines so you can diagnose without a separate starsystem_tail_logs call.


Stop a specific service.

Inputs: id: string


Start all services configured for local mode (or auto mode without cloud credentials) that are not already running.

Returns { started: string[], failed: [{ id, error, logs? }] }.


Run the configured health check for a service immediately.

Inputs: id: string

Never claim a service is working without calling this. The health check verifies actual reachability, not just process existence.


Fetch the most recent log lines for a service.

Inputs: id: string, lines?: number (default 50)

Use this to diagnose startup failures without asking the user to paste logs.


Check which credential environment variables are configured (present) vs missing, for a specific service or all services. Never exposes values — only presence.

Inputs: service_id?: string


Write credential key=value pairs to the .env file and reload them into the running environment.

Inputs: credentials: Record<string, string>

Only call this with values explicitly provided by the user — never speculatively or with placeholder values. Values are write-only and cannot be read back.


List the available built-in system templates with their service compositions.

Apply a built-in template to create a new starsystem.yaml.

Inputs: template: string

⚠️ Replaces the current system definition. Confirm with the user first.


List all starsystem.<env>.yaml overlay files in the project directory, with phase stats (how many services have _tf, _ansible, _cicd blocks).


Read the raw YAML and parsed content of an environment overlay file.

Inputs: env: string


Set the _tf, _ansible, or _cicd block for a service in an environment overlay. Creates the overlay file if it doesn’t exist.

Inputs: env: string, service_id: string, field: "_tf" | "_ansible" | "_cicd", value: object


Add a directed edge between two services.

Inputs: from: string, to: string, connection_type?: string, label?: string

Connections are visual and semantic — they communicate dependencies and data flow to humans and agents reading the topology.


Remove a connection between two services.

Inputs: from: string, to: string


Get the execution plan for a given environment — which services participate in Terraform, Ansible, and CI/CD phases.

Inputs: env: string

Use this before starsystem run to understand what will execute.


Bring all services in the loaded starsystem.yaml to their desired state.

Inputs:

  • service_id?: string — restrict to one service (default: all)
  • env?: string — environment overlay name (default: "local")
  • dry_run?: boolean — show plan without executing (default: false)

Routes automatically by service shape:

  • type: process + command: → starts the process (LocalProcessProvisioner)
  • type: cdn + _cloudflare: → Cloudflare API (custom hostnames, DNS, Pages)
  • provision.provider: neon → Neon Postgres, etc.

Services are applied in depends_on topological order. Idempotent.

Returns:

{
"project": "my-app",
"env": "local",
"outcomes": [
{ "serviceId": "caddy", "status": "provisioned", "summary": "caddy started (pid 9823)" },
{ "serviceId": "postgres", "status": "already-exists", "summary": "postgres already running (pid 1234)" }
]
}

Status values: provisioned | already-exists | skipped | error


Provision a single named service immediately. Shorter to call than starsystem_provision with service_id.

Inputs: service_id: string, env?: string

Use after starsystem_add_service to start the new service right away.


Check the live health of all provisioned services.

Inputs: env?: string

Returns:

{
"summary": "2/3 services healthy",
"services": [
{ "serviceId": "caddy", "provider": "local-process", "healthy": true, "message": "running (pid 9823, health ok)" },
{ "serviceId": "caddy-check-server", "provider": "local-process", "healthy": true, "message": "running (pid 9831)" },
{ "serviceId": "cloudflare-for-saas", "provider": "cloudflare", "healthy": false, "message": "status: pending" }
]
}

Browse all deployable providers and SaaS services with pricing. Use this before writing YAML to discover what’s available and get correct provider names and example snippets.

Inputs: category?: string

Categories: compute | database | dns | auth | email | storage | queue | payments | observability | llm | platform

Returns:

{
"provisioners": [
{
"provider": "porkbun",
"name": "Porkbun",
"description": "Domain registration and DNS management...",
"resources": ["domain", "dns-zone"],
"vaultKeys": [
{ "key": "api_key", "description": "Porkbun API key (pk1_...)" },
{ "key": "PORKBUN_SECRET_KEY", "description": "Porkbun secret key (sk1_...)" }
],
"example": "services:\n domain:\n type: dns\n ..."
}
],
"catalog": [
{
"provider": "porkbun",
"label": "Porkbun Domains",
"resources": [
{ "id": "io", "name": ".io", "pricing": { "monthly": 2.99, "note": "$35.88/yr renewal" } }
]
}
]
}

Typical use:

starsystem_catalog category="dns"
→ see Porkbun domain options and pricing
starsystem_catalog category="database"
→ compare Neon tiers, Upstash Redis pricing
starsystem_catalog
→ full list of all providers and services

Create a new service and start it:

starsystem_read_system
→ starsystem_read_yaml # understand current config precisely
→ starsystem_validate_yaml # check proposed changes
→ starsystem_apply_yaml # push config update
→ starsystem_provision_service # start the new service
→ starsystem_provision_status # verify health
→ starsystem_test_connection # confirm reachable

Diagnose a failed service:

starsystem_service_status # confirm it's stopped/errored
→ starsystem_tail_logs # read last 50 log lines
→ starsystem_provision_service # attempt restart after fixing config
→ starsystem_test_connection # verify recovered

Set up a new environment:

starsystem_list_environments
→ starsystem_read_overlay env=prod # check existing overlay
→ starsystem_set_service_phase # add _tf / _ansible blocks
→ starsystem_get_phase_plan env=prod # review what will run

Register a domain and wire DNS:

starsystem_catalog category="dns" # browse Porkbun options and pricing
→ starsystem_add_service # add dns service with porkbun provider
→ starsystem_provision_service # register domain + create DNS records
→ starsystem_provision_status # verify domain is active