crossplane-mcp-server
Un servidor de Model Context Protocol que permite a los asistentes de IA comprender un plano de control de Crossplane.
Documentación
crossplane-mcp-server
Un servidor de Model Context Protocol que permite a los asistentes de IA comprender un plano de control de Crossplane.
Pregúntale a tu asistente "¿cuántos recursos gestionados tengo y hay algo roto?" y te responderá desde tu plano de control real, con el motivo de cada fallo, en lugar de adivinar.
> Why is the app-db claim not ready?
crossplane_diagnose(kind="PostgreSQLInstance", name="app-db")
PostgreSQLInstance app-db is NOT READY.
Verdict: Instance/app-db-rds is the deepest failure: InvalidParameterValue:
the instance class db.t2.mega does not exist
Root causes (deepest failing resources):
KIND NAME READY SYNCED REASON DETAIL
Instance app-db-rds False False ApplyFailure InvalidParameterValue...
Control plane checks:
CHECK STATE DETAIL
composition OK Composition "postgres-aws" exists.
providers OK all 3 provider(s) are Installed and Healthy
Fix the instanceClass field in your Composition and the claim will reconcile.
Cada herramienta es de solo lectura. Este servidor no puede crear, actualizar ni eliminar nada en tu plano de control.
Contenido
- ¿Por qué no un servidor MCP genérico de Kubernetes?
- Inicio rápido
- Instalación
- Configuración del cliente
- Herramientas
- Prompts
- Llamar a una herramienta directamente
- Configuración
- Múltiples planos de control
- Ejecutar en un clúster
- RBAC requerido
- Contribuir
- Seguridad
- Licencia
¿Por qué no un servidor MCP genérico de Kubernetes?
Un servidor MCP de Kubernetes de propósito general ya puede alcanzar todos los objetos en un
plano de control de Crossplane: los recursos de Crossplane son recursos de Kubernetes, y un
resources_list genérico con un apiVersion y un kind devolverá felizmente
tus XRDs. El acceso nunca fue el problema.
El problema es que no sabe lo que nada de eso significa, y felizmente lo eliminará.
| MCP genérico de Kubernetes | Este servidor | |
|---|---|---|
| Alcanzar CRDs de Crossplane | Sí | Sí |
| Seguir una reclamación hasta la infraestructura que creó | No. Devuelve objetos; el modelo tiene que adivinar qué campo seguir en cada salto | crossplane_resource_tree recorre resourceRefs por ti |
| Decir qué recurso es realmente el culpable | No | crossplane_diagnose encuentra el fallo más profundo, no el síntoma en la superficie |
| Notar que la infraestructura cambió fuera de Crossplane | No. Puede devolver spec y status pero no tiene idea de que deben coincidir | crossplane_drift_detect compara lo deseado con lo observado |
| Explicar por qué una eliminación está bloqueada | No | crossplane_deleting_resources nombra el Usage, finalizer o proveedor que la retiene |
| Decir qué destruiría una eliminación primero | No | crossplane_impact informa el radio de explosión antes de que actúes |
| Simular un cambio sin tocar el clúster | No | crossplane_composition_render ejecuta el pipeline de funciones sin conexión |
| Escribir en tu clúster | Sí: crear, actualizar, eliminar, exec | Nunca. No hay ruta de código que mute nada |
Esa última fila importa más aquí que en el trabajo ordinario con Kubernetes. En un plano de control de Crossplane, un objeto eliminado no es un pod que un ReplicaSet recreará, es una base de datos de producción. Una superficie de herramientas que no puede mutar es una a la que puedes apuntar a tu plano de control de producción sin una revisión de cambios.
En el fondo, el conocimiento de Crossplane que este servidor codifica es:
- Descubre recursos por categoría de Crossplane (
managed,composite,claim), por lo que funciona con cada proveedor sin que se le enseñe ninguno. - Lee
Ready/Synceden recursos yInstalled/Healthyen paquetes, y explica la diferencia al modelo. - Recorre
resourceRefspara construir el árbol de composición, la misma vista quecrossplane beta trace. - Sabe que la deriva en un recurso en pausa o solo
Observenunca se corrige, que es la diferencia entre una advertencia y un no-evento. - Soporta tanto los diseños de Crossplane v1 como v2, incluidos los recursos compuestos
con espacio de nombres y la ubicación de referencia
spec.crossplane.
Inicio rápido
go install github.com/ravibagri5/crossplane-mcp-server/cmd/crossplane-mcp-server@latest
# See what this build exposes
crossplane-mcp-server tools
# Check it can reach your control plane
crossplane-mcp-server call crossplane_status
Luego agrégalo a tu cliente MCP (consulta Configuración del cliente) y pregúntale sobre tu plano de control.
Instalación
Requisitos
- Go 1.26 o más reciente, si instalas desde el código fuente o con
go install. Los binarios precompilados y la imagen de contenedor no tienen tal requisito. - Acceso a un clúster de Kubernetes con Crossplane instalado. Cualquier versión de Crossplane v1 o v2 funciona.
- Opcional: el CLI de crossplane y un
runtime de contenedores, utilizado solo por
crossplane_composition_render. El renderizado ejecuta el pipeline de funciones de composición, que no se puede hacer a través de la API de Kubernetes. Cada otra herramienta no necesita nada más que acceso a la API, ycrossplane_composition_validatecubre la mayor parte del mismo terreno sin un runtime de contenedores.
Instalación con Go
go install github.com/ravibagri5/crossplane-mcp-server/cmd/crossplane-mcp-server@latest
Imagen de contenedor
docker run --rm -i \
-v "${HOME}/.kube:/home/nonroot/.kube:ro" \
ghcr.io/ravibagri5/crossplane-mcp-server:latest
Binarios
Los binarios precompilados para Linux, macOS y Windows están adjuntos a cada release. Estas son la opción más fácil si no tienes un toolchain de Go reciente.
Desde el código fuente
git clone https://github.com/ravibagri5/crossplane-mcp-server.git
cd crossplane-mcp-server
make build
./bin/crossplane-mcp-server tools
Registros
Este servidor está listado en:
- Registro MCP oficial
como
io.github.ravibagri5/crossplane-mcp-server, que es donde los clientes MCP lo buscan. - Smithery, que también ofrece instalación con un clic en un cliente.
- pkg.go.dev para la documentación del paquete Go.
Configuración del cliente
Claude Desktop, Claude Code, Cursor, Windsurf
{
"mcpServers": {
"crossplane": {
"command": "crossplane-mcp-server",
"args": ["--clusters", "staging,production", "--context", "staging"],
"env": {
"PATH": "/opt/homebrew/bin:/usr/local/bin:/usr/bin:/bin",
"HOME": "/Users/you"
}
}
}
}
PATH y HOME importan siempre que un contexto de kubeconfig autentique a través de un
plugin exec como kubelogin o aws. Las aplicaciones de escritorio lanzan servidores
con un entorno casi vacío, por lo que sin ellos el plugin no se encuentra
o no puede leer su caché de tokens.
Goose
En ~/.config/goose/config.yaml:
extensions:
crossplane:
enabled: true
type: stdio
cmd: /path/to/crossplane-mcp-server
args: ["--clusters", "staging,production", "--context", "staging"]
envs:
PATH: /opt/homebrew/bin:/usr/local/bin:/usr/bin:/bin
HOME: /Users/you
timeout: 300
VS Code
Agrega a .vscode/mcp.json en tu espacio de trabajo:
{
"servers": {
"crossplane": {
"type": "stdio",
"command": "crossplane-mcp-server",
"args": ["--clusters", "staging,production"]
}
}
}
Clientes basados en contenedores
{
"mcpServers": {
"crossplane": {
"command": "docker",
"args": [
"run", "--rm", "-i",
"-v", "${HOME}/.kube:/home/nonroot/.kube:ro",
"ghcr.io/ravibagri5/crossplane-mcp-server:latest"
]
}
}
}
Herramientas
Ejecuta crossplane-mcp-server tools para imprimir esta lista desde tu compilación.
resources
Recursos gestionados, recursos compuestos y reclamaciones.
| Herramienta | Qué responde |
|---|---|
crossplane_managed_resources_summary | Cuántos recursos gestionados existen, por tipo, y cuántos están Listos y Sincronizados |
crossplane_managed_resources_list | Qué recursos gestionados existen, opcionalmente solo los que fallan |
crossplane_composite_resources_list | Qué recursos compuestos (XRs) existen y qué Composition seleccionó cada uno |
crossplane_claims_list | Qué reclamaciones existen y a qué compuesto está vinculada cada una |
crossplane_resource_get | Todo sobre un recurso: condiciones, nombre externo, eventos, manifiesto |
crossplane_resource_tree | El árbol de composición debajo de una reclamación o compuesto, con estado por recurso |
crossplane_resource_events | Los eventos que Crossplane registró contra un recurso |
crossplane_diagnose | Por qué un recurso no está Listo, y qué recurso es realmente el culpable |
crossplane_drift_detect | Qué infraestructura ya no coincide con su spec declarado, y si eso se corregirá |
packages
| Herramienta | Qué responde |
|---|---|
crossplane_providers_list | Qué proveedores están instalados y saludables |
crossplane_functions_list | Qué funciones de composición están instaladas y saludables |
crossplane_configurations_list | Qué configuraciones están instaladas y saludables |
crossplane_package_get | Un paquete más sus revisiones, donde aparecen los errores de extracción de imagen y dependencias |
compositions
| Herramienta | Qué responde |
|---|---|
crossplane_xrds_list | Qué APIs de plataforma ofrece este plano de control |
crossplane_xrd_schema | Los campos que toma una API de plataforma, con un manifiesto de ejemplo listo para editar |
crossplane_compositions_list | Qué Compositions existen y qué pipeline ejecutan |
crossplane_composition_get | La definición completa de una Composition |
crossplane_composition_validate | Por qué una Composition no funciona, sin ejecutar nada |
crossplane_composition_render | Qué crearía realmente una Composition, como ejecución en seco |
config
Cómo está configurado el propio plano de control.
| Herramienta | Qué responde |
|---|---|
crossplane_environment_configs_list | Qué EnvironmentConfigs existen y qué datos contienen |
crossplane_deployment_runtime_configs_list | Qué configuraciones de runtime existen y qué paquetes las usan |
crossplane_managed_resource_definitions_list | Qué tipos de recursos gestionados están Activos, en Crossplane v2 |
crossplane_managed_resource_activation_policies_list | Qué políticas activan esas definiciones |
diagnostics
| Herramienta | Qué responde |
|---|---|
crossplane_clusters_list | A qué planos de control puede llegar este servidor |
crossplane_status | La salud general del plano de control en una llamada |
crossplane_unhealthy_resources | Todo lo que está fallando actualmente, y por qué |
crossplane_deleting_resources | Qué está atascado eliminando, y qué lo retiene |
crossplane_usages_list | Qué está protegido de la eliminación, y qué lo necesita |
crossplane_impact | Qué destruiría una eliminación, y si estaría bloqueada |
crossplane_api_resources | La superficie de API de Crossplane, para encontrar tipos y grupos exactos |
Expón un subconjunto con --toolsets:
crossplane-mcp-server --toolsets diagnostics,packages
Prompts
Las herramientas le dicen a un modelo lo que puede hacer. Los prompts le dicen el orden en que un operador experimentado haría las cosas, para que no tenga que redescubrir en cada conversación que diagnosticar una reclamación comienza en la reclamación y no en el recurso gestionado que parece más enojado.
La mayoría de los clientes muestran estos como comandos de barra o un selector de prompts.
| Prompt | Qué hace |
|---|---|
diagnose_resource | Recorre un recurso con fallos hasta el error del proveedor y propone la solución |
control_plane_review | Produce un informe de salud ordenado por lo que necesita atención primero |
explain_platform_api | Explica qué ofrece una API de plataforma y cómo solicitar una |
assess_deletion | Calcula el radio de explosión de una eliminación antes de que alguien la ejecute |
Llamar a una herramienta directamente
call ejecuta una herramienta e imprime lo que devuelve, sin un cliente MCP en el
camino. Úsalo para verificar que el servidor puede llegar a tu clúster, y para ver qué devuelve
realmente una herramienta en lugar de lo que un modelo dice que devolvió.
# No arguments
crossplane-mcp-server call crossplane_status
# Arguments are the same JSON an MCP client would send
crossplane-mcp-server call crossplane_managed_resources_list '{"status":"not-ready"}'
crossplane-mcp-server call crossplane_diagnose '{"kind":"Bucket","name":"app-data"}'
# The structured payload the model receives, instead of the text rendering
crossplane-mcp-server call crossplane_status --json
# Against another control plane
crossplane-mcp-server call crossplane_status --context prod
Ejecuta crossplane-mcp-server tools --json para ver los argumentos exactos que acepta una
herramienta.
Configuración
| Flag | Predeterminado | Descripción |
|---|---|---|
--kubeconfig | $KUBECONFIG, luego ~/.kube/config, luego en-clúster | Ruta a un archivo kubeconfig |
--context | contexto actual | Contexto de kubeconfig utilizado cuando una herramienta no nombra un clúster |
--clusters | cada contexto | Contextos separados por comas para exponer como objetivos |
--namespace | espacio de nombres del contexto, si no default | Espacio de nombres predeterminado para recursos con espacio de nombres |
--toolsets | todos | Conjuntos de herramientas separados por comas para exponer |
--http-address | (sin establecer) | Servir HTTP transmisible en esta dirección en lugar de stdio |
--log-level | info | debug, info, warn o error. Los registros siempre van a stderr |
--tool-timeout | 2m | Tiempo máximo que una sola llamada de herramienta puede ejecutarse. 0 lo desactiva |
--version | Imprimir la versión y salir |
Múltiples planos de control
Un servidor puede hablar con varios planos de control. Cada herramienta toma un argumento
opcional cluster que nombra uno de ellos, y crossplane_clusters_list le dice a un
modelo cuáles están disponibles.
crossplane-mcp-server --clusters staging,production --context staging
Pregúntale a tu asistente "¿está fallando algo en producción?" y pasará
cluster: "production"; omite el clúster y usará--context.
Usa --clusters. Sin él, cada contexto en tu kubeconfig se convierte en un
objetivo, lo que en una máquina con unos cientos de contextos significa que un asistente podría
llegar a un clúster de producción cuando querías un sandbox. Nombrar los pocos con los que
trabajas es más rápido y más seguro.
Los clientes se crean de forma diferida y se almacenan en caché, por lo que un clúster inalcanzable no impide que los demás funcionen, y listar clústeres no cuesta nada.
Credenciales
| Fuente | Cómo funciona |
|---|---|
| Contexto de kubeconfig | Se usa tal cual, incluidos los contextos que se autentican mediante un plugin exec |
| Identidad en la nube (AKS, EKS, GKE) | Funciona a través del plugin exec que ya declara el kubeconfig, como kubelogin o aws |
| Cuenta de servicio | Se usa automáticamente cuando no hay kubeconfig, que es el caso de la implementación dentro del clúster |
Los plugins exec son ejecutables comunes, por lo que un servidor iniciado por una
aplicación de escritorio necesita PATH para incluirlos, y HOME para que puedan encontrar su
propia caché de tokens. La mayoría de los clientes MCP inician servidores con un entorno casi vacío,
que es la razón habitual por la que un clúster funciona en una terminal pero no en el cliente:
{
"command": "crossplane-mcp-server",
"args": ["--clusters", "staging,production"],
"env": {
"PATH": "/opt/homebrew/bin:/usr/local/bin:/usr/bin:/bin",
"HOME": "/Users/you"
}
}
Ejecución en un clúster
Sirve el transporte HTTP transmisible cuando el servidor se ejecuta dentro del plano de control que inspecciona:
crossplane-mcp-server --http-address :8080
El endpoint MCP es /mcp y un endpoint de liveness se sirve en /healthz. El
servidor usa la cuenta de servicio del pod cuando no hay kubeconfig presente. Los manifiestos
están en deploy/.
El transporte HTTP no tiene autenticación integrada. Colócalo detrás de un proxy autenticador, o mantenlo en una red privada. Consulta SECURITY.md.
RBAC requerido
El servidor solo lee. Un rol de clúster que cubre todas las herramientas:
apiVersion: rbac.authorization.k8s.io/v1
kind: ClusterRole
metadata:
name: crossplane-mcp-server
rules:
# Discovery, so the server can find managed and composite resource kinds.
- apiGroups: ["apiextensions.k8s.io"]
resources: ["customresourcedefinitions"]
verbs: ["get", "list"]
# Everything Crossplane owns.
- apiGroups: ["*.crossplane.io"]
resources: ["*"]
verbs: ["get", "list"]
# Managed resources, which live in provider-specific API groups.
- apiGroups: ["*"]
resources: ["*"]
verbs: ["get", "list"]
- apiGroups: [""]
resources: ["events"]
verbs: ["get", "list"]
- apiGroups: ["apps"]
resources: ["deployments"]
verbs: ["get", "list"]
Si prefieres no otorgar una lectura a nivel de clúster, deploy/rbac-minimal.yaml
reduce los permisos a costa de que algunas herramientas devuelvan advertencias.
Contribuciones
Las contribuciones son muy bienvenidas. Comienza con CONTRIBUTING.md,
que cubre el flujo de trabajo de desarrollo, cómo agregar una herramienta y el requisito de
firma. Los primeros problemas buenos están etiquetados
good first issue.
Este proyecto sigue el Código de Conducta de Crossplane y está gobernado como se describe en GOVERNANCE.md.
Seguridad
Informa las vulnerabilidades de forma privada. Consulta SECURITY.md.
Licencia
Licencia Apache 2.0. Consulta LICENSE.
crossplane-mcp-server es un proyecto comunitario y no es un proyecto oficial de
Crossplane o CNCF. Crossplane es una marca registrada de The Linux
Foundation.