Quickstart: MCP Server

Let any MCP-compatible agent (Claude Desktop, Claude Code, etc.) publish the sites it generates straight to live hosting, provision custom domains for them, and send transactional email — in under 5 minutes.

1. Get a Platform API Key

Sign up at thin.host, then open Email & API → Settings in your dashboard to create an API key (one per app or agent — each can be revoked on its own). For testing, you can use the free tier (3 domains, 100 API calls/day).

Sending email (the send_email tool) needs a separate, founder-approved access step beyond the API key. See Get access to email.

2. Connect an agent

Three ways in, all exposing the same tools. The hosted endpoint is the zero-install path and the one to start with.

A. Hosted endpoint (no install)

The MCP server runs at https://thin.host/mcp. Authenticate with your API key as a bearer token, or sign in through OAuth — clients that support it (claude.ai custom connectors, Claude Desktop connectors, Claude Code) discover the OAuth flow automatically and show a thin.host consent page.

# Claude Code, with an API key
claude mcp add --transport http thin-host https://thin.host/mcp \
  --header "Authorization: Bearer th_live_your_key"

# Claude Code, with OAuth (a browser window asks you to allow the connection)
claude mcp add --transport http thin-host https://thin.host/mcp

claude.ai / Claude Desktop: Settings → Connectors → Add custom connector → URL https://thin.host/mcp. You'll be asked to sign in to thin.host and allow access.

The hosted server cannot read your disk, so it publishes from a URL (publish_website_from_url / update_website_from_url — a .zip of the site or a single HTML page). If you connected with an API key rather than OAuth, the agent can also upload a zip straight to the REST API with that key: curl -F file=@site.zip -F title="My Docs" https://thin.host/v1/websites/archive -H "Authorization: Bearer th_live_…".

B. Local server via uvx (reads your files)

Runs the same server on your machine so publish_website can read a local folder or build directory directly — no zipping. Needs uv.

claude mcp add thin-host \
  -e THINHOST_API_URL=https://thin.host/v1 \
  -e THIN_HOST_API_KEY=th_live_your_key \
  -- uvx thinhost-mcp

The package is thinhost-mcp on PyPI; the same wheel is also served at https://thin.host/dl/thinhost-mcp/latest if you would rather pin to the URL.

C. Claude Desktop bundle (.mcpb)

Download a ready-to-install bundle from the dashboard (Email & API → MCP package) and open it in Claude Desktop, or add the server by hand to claude_desktop_config.json:

{
  "mcpServers": {
    "thin-host": {
      "command": "uvx",
      "args": ["thinhost-mcp"],
      "env": {
        "THINHOST_API_URL": "https://thin.host/v1",
        "THIN_HOST_API_KEY": "th_live_your_key_here"
      }
    }
  }
}

3. Use It

In a Claude conversation, ask Claude to build something and put it live:

"Build me a landing page for my bakery and publish it."

Claude writes the site, calls publish_website, and hands you a live URL like https://thin.host/s/sunrise-bakery/. Iterate in the same conversation — "make the header green" — and Claude pushes the change with update_website.

Custom domains work the same way:

"I just deployed my site to https://myapp.vercel.app. Can you set up myportfolio.com as a custom domain?"

Claude will call provision_domain, get back a claim URL, and share it with you. You visit the claim page, pay, configure DNS, and the domain goes live.

Available Tools

ToolDescription
publish_websitePublish a local HTML file, directory, or ZIP as a live hosted site
update_websitePush updated pages/assets to an existing hosted site
list_websitesList your hosted sites with their live URLs
provision_domainCreate a new custom domain with payment/claim flow
check_domain_statusPoll domain provisioning progress
update_originChange the target URL for a domain
release_domainTear down a provisioned domain
list_domainsList all domains with optional filtering
send_emailSend a transactional notification email (requires email access approval)

Example Flow

# Agent provisions a domain
result = await mcp.call("provision_domain", {
    "domain": "mysite.com",
    "origin_url": "https://myapp.vercel.app",
    "user_email": "user@example.com"
})
# → { provision_id, status: "pending_payment", claim_url, dns_instructions }

# Agent shares the claim_url with the user
# User pays and configures DNS

# Agent checks status
status = await mcp.call("check_domain_status", {
    "provision_id": result["provision_id"]
})
# → { status: "active", ready: true }

See the MCP Tool Reference for full parameter and response documentation.