An MCP server for the Bowtie control plane. Manage your Bowtie cluster — policies, devices, DNS, users, and more — using natural language through your LLM of choice or any MCP-capable client.
pip install bowtie-mcpOr run without installing using uvx:
uvx bowtie-mcpclaude mcp add bowtie \
-e BOWTIE_HOST="https://bt0.example.com" \
-e BOWTIE_USERNAME="admin@example.com" \
-e BOWTIE_PASSWORD="your-password" \
-- uvx bowtie-mcpAdd to your claude_desktop_config.json:
{
"mcpServers": {
"bowtie": {
"command": "uvx",
"args": ["bowtie-mcp"],
"env": {
"BOWTIE_HOST": "https://bt0.example.com",
"BOWTIE_USERNAME": "admin@example.com",
"BOWTIE_PASSWORD": "your-password"
}
}
}
}Add to .cursor/mcp.json or your editor's MCP config:
{
"mcpServers": {
"bowtie": {
"command": "uvx",
"args": ["bowtie-mcp"],
"env": {
"BOWTIE_HOST": "https://bt0.example.com",
"BOWTIE_USERNAME": "admin@example.com",
"BOWTIE_PASSWORD": "your-password"
}
}
}
}For clients that connect over HTTP instead of spawning a local stdio process, start the server in one of FastMCP's HTTP transports:
uvx bowtie-mcp --transport streamable-http --port 8080This binds to 127.0.0.1:8080 and exposes the recommended Streamable HTTP endpoint at http://127.0.0.1:8080/mcp.
Legacy SSE is also available:
uvx bowtie-mcp --transport sse --port 8080The SSE endpoint is http://127.0.0.1:8080/sse. During the handshake, FastMCP tells the client to post subsequent messages to the matching http://127.0.0.1:8080/messages/ endpoint.
The server authenticates to your Bowtie controller using admin credentials — the same approach used by the Bowtie Terraform provider.
| Variable | Required | Description |
|---|---|---|
BOWTIE_HOST |
Yes | Controller HTTPS endpoint (e.g., https://bt0.example.com) |
BOWTIE_USERNAME |
Yes | Admin email address |
BOWTIE_PASSWORD |
Yes | Admin password |
BOWTIE_MCP_SKIP_CONFIRMATION |
No | Set to true to skip write confirmation prompts |
Credentials are used by the local MCP server process to authenticate with your controller. They are never sent to or visible by the LLM.
Ask your LLM things like:
- "List all pending devices and approve the ones from the engineering team"
- "Create a policy that gives the sales team access to the CRM on 10.0.5.0/24 port 443"
- "Why can't device X reach the production database?"
- "Audit our policies for anything overly permissive"
- "Set up DNS for internal.example.com pointing at 10.0.0.53"
Read (30+ tools) — List and inspect users, devices, device groups, user groups, policies, resources, resource groups, DNS configs, sites, collections, block lists, threat categories, controllers, route exclusions, and API keys.
Write (25+ tools) — Create, update, and delete all of the above. All write operations require explicit confirmation before executing (see below).
Guided Workflows (4 prompts):
| Prompt | Description |
|---|---|
onboard-team |
Create a user group, resources, resource group, and access policy |
audit-policies |
Review all policies for overly permissive rules |
troubleshoot-access |
Diagnose why a user/device can or can't reach a destination |
review-pending-devices |
Batch approve or reject pending devices |
All write tools use a two-step confirmation pattern. The first call returns a preview of the planned change. Call again with confirm=true to execute. This prevents accidental mutations.
Tool responses are returned as structured JSON-compatible objects rather than pre-serialized JSON strings, so MCP clients can inspect fields directly.
Set BOWTIE_MCP_SKIP_CONFIRMATION=true to bypass this for automation or CI workflows.
git clone https://github.com/bowtieworks/bowtie-mcp.git
cd bowtie-mcp
pip install -e ".[dev]"
pytestSee CONTRIBUTING.md for more details.