Database MCP

Kubernetes

Deploy dbmcp on Kubernetes with the Helm chart

The Helm chart runs dbmcp with the http transport behind a Service. HTTP mode is stateless, so you can run several replicas without session affinity.

Install

The chart is published as an OCI artifact on GitHub Container Registry:

helm install dbmcp oci://ghcr.io/haymon-ai/charts/dbmcp \
  --namespace dbmcp --create-namespace \
  --values values.yaml

A minimal values.yaml:

values.yaml
config:
  database:
    backend: postgres
    host: postgres.db.svc.cluster.local
    user: dbmcp
    name: app

database:
  password: change-me

auth:
  token: change-me # e.g. openssl rand -hex 32

Clients then connect to http://dbmcp.dbmcp.svc.cluster.local:9001/mcp with Authorization: Bearer <token>. To try it from your machine:

kubectl --namespace dbmcp port-forward svc/dbmcp 9001

Then point your MCP client at http://localhost:9001/mcp.

Pin a chart version with --version <version>. The chart version always matches the dbmcp version, and the chart deploys that same image tag by default.

Configuration

config holds a regular config file. The chart renders it into a ConfigMap and points DBMCP_CONFIG_FILE at it, so every setting works there. The chart sets these settings itself through environment variables, which take precedence over the file:

SettingValue
transporthttp
http.host0.0.0.0
http.portservice.port (default 9001)
http.allowed_hostsThe Service DNS names, localhost, 127.0.0.1, ::1, every non-wildcard ingress.hosts[].host, and the entries of config.http.allowed_hosts

dbmcp matches Host headers exactly. If clients reach it under another name, such as a gateway hostname, add that name to config.http.allowed_hosts. Browser clients also need their origin in config.http.allowed_origins.

Pods roll automatically when config changes.

Secrets

auth.token and database.password go into a Secret the chart creates. They reach dbmcp as DBMCP_HTTP_AUTH_TOKEN and DBMCP_DB_PASSWORD. To manage the Secret yourself, for example with External Secrets or Sealed Secrets, reference it instead:

values.yaml
existingSecret:
  name: dbmcp-credentials
  authTokenKey: auth-token   # required
  passwordKey: db-password   # optional

The chart refuses to render without a token, because dbmcp will not serve a non-loopback address without one (see HTTP Transport Authentication). auth.dangerouslyAllowUnauthenticated: true removes that check.

For other secret settings, such as an SSH key passphrase, add extraEnv entries with secretKeyRef. Mount key and certificate files with extraVolumes and extraVolumeMounts, and reference their paths in config.

Ingress

values.yaml
ingress:
  enabled: true
  className: nginx
  hosts:
    - host: dbmcp.example.com
      paths:
        - path: /
          pathType: Prefix
  tls:
    - secretName: dbmcp-tls
      hosts:
        - dbmcp.example.com

The Ingress hosts are added to the allowed hosts automatically. Wildcard hosts such as *.example.com are skipped, because dbmcp matches hosts exactly; list each concrete name in config.http.allowed_hosts. dbmcp answers with plain JSON instead of server-sent event streams, so the Ingress needs no buffering or timeout tweaks.

Probes

The liveness and startup probes call /healthz, and the readiness probe calls /readyz, which checks the database (see Health Probes). A pod becomes Ready only once its database answers, and leaves the Service when the database stops answering. Override the timings with livenessProbe, readinessProbe, and startupProbe.

Security

By default the pod:

  • runs as the image's non-root user (uid and gid 65532)
  • has a read-only root filesystem
  • drops all Linux capabilities and blocks privilege escalation
  • uses the RuntimeDefault seccomp profile
  • does not mount a service account token

dbmcp needs no writable paths. For SSH tunnelling, mount a pre-filled known_hosts file beside the key (see Secrets). Avoid accept-new (see SSH Host-Key Verification): every new pod would trust the first key it sees.

Verify the Chart

Each chart carries a keyless cosign signature and a build provenance attestation, verified like the image (see Verify Downloads).

See values.yaml for every value.

On this page