mcp-k8s-deployer
Enables LLMs to dynamically orchestrate containerized application deployments to a Kubernetes cluster, handling configuration validation, manifest generation, dry-run planning, and service endpoint extraction.
README
mcp-k8s-deployer
A production-ready Model Context Protocol (MCP) server that empowers LLMs to dynamically orchestrate containerized application deployments to a Kubernetes cluster.
It handles configuration validation, interactive storage resolution, multi-resource manifest generation (Namespace, PersistentVolumeClaim, Deployment, Service), dry-run plan reviews, actual apply actions, and service endpoint extraction optimized for cloudflared tunnel routing.
Features
- Interactive Storage Resolution: Dynamically checks whether to create a new PVC, bind to an existing PV, or prompt the user for more details depending on whether the StorageClass matches the cluster's default NFS setup.
- Strict Input Validation: Enforces RFC 1123 compliant naming for apps, namespaces, and StorageClasses, validates port ranges, replicas, image tags, and Kubernetes storage sizes (e.g.
10Gi). - Dry-run Planning & Actual Applying: Exposes separate planning (
plan_deployment) and apply (apply_deployment) stages. Planning runs a Kubernetes server-side dry-run to catch configuration errors before changes are committed. - Enforced Review Step: The
apply_deploymenttool requires an explicitapproved=Trueparameter to enforce user verification of planned changes. - Tunnel Mapping Helpers: Auto-formats endpoints to seamlessly configure public subdomains with
cloudflaredtunnels.
Prerequisites
- Python: Version 3.10 or higher.
- Kubernetes Cluster: Access to a running cluster (e.g., k3s, minikube, GKE, EKS) with cluster credentials.
- Credentials: A valid kubeconfig file (defaults to
~/.kube/config).
Installation
From PyPI (recommended)
pip install mcp-k8s-deployer
From source
git clone https://github.com/stwins60/mcp-k8s-deployer.git
cd mcp-k8s-deployer
python3 -m venv .venv
source .venv/bin/activate
pip install -r requirements.txt
Verify installation
python3 -m pytest -v
Configuration
The server supports configuration through environment variables or a YAML configuration file.
Environment Variables
| Variable | Description | Default |
|---|---|---|
MCP_K8S_LOG_LEVEL |
Logging level (DEBUG, INFO, WARNING, ERROR) |
INFO |
MCP_K8S_DEFAULT_NFS_STORAGE_CLASS |
StorageClass name treated as default NFS-backed storage | nfs |
MCP_K8S_ALLOWED_NAMESPACES |
Comma-separated list of allowed namespaces. If empty, all are allowed. | "" |
KUBECONFIG or MCP_K8S_KUBECONFIG_PATH |
Path to the active cluster kubeconfig file | ~/.kube/config |
MCP_K8S_DEFAULT_REPLICAS |
Default pod replicas count if unspecified | 1 |
MCP_K8S_DEFAULT_PORT |
Default service port if unspecified | 80 |
MCP_K8S_DEFAULT_STORAGE_SIZE |
Default persistent volume size | 10Gi |
YAML Configuration File
Create a config.yaml file in the root of the project (or store it in /etc/mcp-k8s/config.yaml):
logging:
level: "INFO"
kubernetes:
kubeconfig_path: "" # Empty uses default ~/.kube/config
default_nfs_storage_class: "nfs"
allowed_namespaces: []
defaults:
replicas: 1
container_port: 80
storage_size: "10Gi"
Exposed MCP Tools
1. choose_storage_option_tool
Assesses storage configuration based on StorageClass and PV requirements.
- Arguments:
storage_class(str, required): The target storage class name (e.g.nfs,local-path).has_existing_pv(bool, required): Whether the user has an existing PersistentVolume (PV) created.existing_pv_name(str, optional): The name of the existing PV to bind statically.storage_size(str, optional): Desired disk size (e.g.5Gi).default_nfs_class(str, optional): Override the default NFS storage class config.
- Returns: A JSON dictionary advising on PVC generation, PV binding, or actions required.
2. deploy_app_tool
Gathers configurations, validates inputs, and generates Kubernetes manifests in YAML format.
- Arguments:
app_name(str, required)image(str, required)container_port(int, required)replicas(int, optional)namespace(str, optional)use_persistence(bool, optional)storage_class(str, optional)storage_size(str, optional)existing_pv_name(str, optional)env_vars(dict, optional)hostname(str, optional)
- Returns: A multi-document YAML string representing the Namespace, PVC, Deployment, and Service.
3. plan_deployment_tool
Validates inputs, generates manifests, and runs a server-side dry-run apply against the cluster.
- Arguments: Same as
deploy_app_tool. - Returns: The generated manifests, dry-run actions list (e.g.,
Created,Patched), and validation status.
4. apply_deployment_tool
Applies approved manifests to the Kubernetes cluster.
- Arguments:
manifests(str, required): The generated YAML manifests.approved(bool, required): Must be set toTrueto confirm.
- Returns: Success status and array of resources created or patched.
5. create_namespace_tool
Creates a namespace if it doesn't already exist.
- Arguments:
namespace(str, required)dry_run(bool, optional)
6. get_service_endpoint_tool
Computes the internal cluster Service DNS endpoint.
- Arguments:
app_name(str),namespace(str),container_port(int). - Returns: The service URL (e.g.
http://app.namespace.svc.cluster.local:80).
7. build_cloudflared_target_tool
Generates the exact target string to paste into a cloudflared tunnel mapping configuration.
- Arguments:
app_name(str),namespace(str),container_port(int).
Claude Desktop Integration
Using the pip-installed package
Add the following to your Claude Desktop config (~/.config/Claude/claude_desktop_config.json on Linux):
{
"mcpServers": {
"kubernetes-deployer": {
"command": "mcp-k8s-deployer",
"env": {
"MCP_K8S_DEFAULT_NFS_STORAGE_CLASS": "nfs",
"MCP_K8S_LOG_LEVEL": "INFO"
}
}
}
}
Using a local source checkout
{
"mcpServers": {
"kubernetes-deployer": {
"command": "/path/to/.venv/bin/python3",
"args": [
"/path/to/mcp-k8s-deployer/src/server.py"
],
"env": {
"MCP_K8S_DEFAULT_NFS_STORAGE_CLASS": "nfs",
"MCP_K8S_LOG_LEVEL": "INFO"
}
}
}
}
Transport Selection (Stdio vs SSE)
By default, the server runs over standard input/output (stdio) transport, suitable for local integrations like Claude Desktop.
Running over Stdio (default)
python3 src/server.py --transport stdio
Running over SSE (HTTP web server)
python3 src/server.py --transport sse --host 0.0.0.0 --port 8000
Or use environment variables:
export MCP_TRANSPORT=sse
export MCP_PORT=8000
python3 src/server.py
The MCP endpoint will be accessible at http://<your-host>:8000/sse.
Typical Execution Flow
- User Request: "Deploy my Node.js app
auth-serviceusingnode:18in thedevnamespace. It needs 5Gi of gp2 storage." - Storage Decision: The LLM calls
choose_storage_option_tool(storage_class="gp2", has_existing_pv=False, storage_size="5Gi"). - Storage Advice: The server advises that
gp2is non-default and will rely on dynamic provisioning. The LLM presents this to the user. - Planning: The user confirms. The LLM calls
plan_deployment_tool(...), which returns the planned resources and dry-run status. - Confirmation: The LLM presents the YAML manifests for user review.
- Execution: The user confirms. The LLM calls
apply_deployment_tool(manifests="...", approved=True). - Mapping: The LLM calls
build_cloudflared_target_tool(...)and prints the Cloudflare Tunnel ingress target (e.g.,http://auth-service.dev.svc.cluster.local:80).
Distribution
PyPI
The package is published to PyPI automatically via GitHub Actions on every new GitHub Release using OIDC trusted publishing — no API tokens required.
To release a new version:
- Update
versioninpyproject.toml - Commit and push to
master - Create a new GitHub Release with a version tag (e.g.,
v1.0.1)
The workflow at .github/workflows/publish.yml will build and upload to PyPI automatically.
Docker
# Build the container image
docker build -t your-dockerhub-username/mcp-k8s-deployer:latest .
# Push to Docker Hub
docker push your-dockerhub-username/mcp-k8s-deployer:latest
Docker Compose & Cloudflare Tunnel
- Create a
.envfile with your Cloudflare token:CLOUDFLARE_TUNNEL_TOKEN=your_cloudflare_tunnel_token_here - Start the services:
docker compose up -d - In your Cloudflare Zero Trust Dashboard, configure a Public Hostname:
- Domain:
mcp.yourdomain.com - Service Type:
HTTP - URL:
mcp-server:8000
- Domain:
Your MCP server will be accessible at https://mcp.yourdomain.com/sse.
Links
- PyPI: https://pypi.org/project/mcp-k8s-deployer/
- GitHub: https://github.com/stwins60/mcp-k8s-deployer
- Issues: https://github.com/stwins60/mcp-k8s-deployer/issues
License
MIT
推荐服务器
Baidu Map
百度地图核心API现已全面兼容MCP协议,是国内首家兼容MCP协议的地图服务商。
Playwright MCP Server
一个模型上下文协议服务器,它使大型语言模型能够通过结构化的可访问性快照与网页进行交互,而无需视觉模型或屏幕截图。
Magic Component Platform (MCP)
一个由人工智能驱动的工具,可以从自然语言描述生成现代化的用户界面组件,并与流行的集成开发环境(IDE)集成,从而简化用户界面开发流程。
Audiense Insights MCP Server
通过模型上下文协议启用与 Audiense Insights 账户的交互,从而促进营销洞察和受众数据的提取和分析,包括人口统计信息、行为和影响者互动。
VeyraX
一个单一的 MCP 工具,连接你所有喜爱的工具:Gmail、日历以及其他 40 多个工具。
graphlit-mcp-server
模型上下文协议 (MCP) 服务器实现了 MCP 客户端与 Graphlit 服务之间的集成。 除了网络爬取之外,还可以将任何内容(从 Slack 到 Gmail 再到播客订阅源)导入到 Graphlit 项目中,然后从 MCP 客户端检索相关内容。
Kagi MCP Server
一个 MCP 服务器,集成了 Kagi 搜索功能和 Claude AI,使 Claude 能够在回答需要最新信息的问题时执行实时网络搜索。
e2b-mcp-server
使用 MCP 通过 e2b 运行代码。
Neon MCP Server
用于与 Neon 管理 API 和数据库交互的 MCP 服务器
Exa MCP Server
模型上下文协议(MCP)服务器允许像 Claude 这样的 AI 助手使用 Exa AI 搜索 API 进行网络搜索。这种设置允许 AI 模型以安全和受控的方式获取实时的网络信息。