ENGINEERING SPECS
Control Plane Deployment Specification
1. Goal
This document defines the production deployment contract for api.orbitmesh.dev.
The Control Plane is a Go Kratos service and should run as a containerized backend service. It should not be deployed to Cloudflare Workers.
2. Deployment Shape
Production:
console.orbitmesh.dev Cloudflare Pages Tenant Console
platform.orbitmesh.dev Cloudflare Pages Platform Console
install.orbitmesh.dev Cloudflare Workers installer entrypoint
downloads.orbitmesh.dev object storage or CDN artifact prefix
api.orbitmesh.dev containerized Go Kratos Control Plane
Supported Control Plane runtime targets:
- Cloud Run.
- Fly.io.
- Railway.
- Render.
- VPS with Docker Compose or systemd.
The first production deployment may use any container platform that provides HTTPS ingress, environment variables, logs, and restart management.
3. Container Image
Production Control Plane images are built and published by:
.github/workflows/release-control-plane.yml
The workflow follows the same mkctr pattern as other OrbitMesh services:
builder: orbitmesh/mkctr:1.24.7-alpine
base: orbitmesh/alpine-base:3.22
image: ghcr.io/orbitmesh-official/orbitmesh-api
The repository still keeps a Dockerfile for local, compatibility, and manual builds:
services/control-plane/Dockerfile
The image contains:
orbitmesh-api- default config directory at
/etc/orbitmesh/control-plane
Default process:
/app/orbitmesh-api -conf /etc/orbitmesh/control-plane
Exposed ports:
8080 HTTP
9000 gRPC
Production public ingress should expose only HTTP port 8080 unless gRPC is intentionally enabled.
4. Required Dependencies
Required:
- PostgreSQL by default, or MySQL 8.
Recommended:
- Redis.
The SQL database is the source of truth. Redis is used for short-lived runtime state such as nonce, rate limit, cache, and distributed coordination. If Redis is unavailable, the deployment platform must make the limitation explicit before production traffic is enabled.
5. Environment Variables
Required production variables:
ORBITMESH_DATABASE_DRIVER=pgx
ORBITMESH_DATABASE_URL
ORBITMESH_REDIS_ADDR
ORBITMESH_PUBLIC_URL=https://api.orbitmesh.dev
ORBITMESH_JWT_SECRET
ORBITMESH_HTTP_ADDR=0.0.0.0:8080
ORBITMESH_GRPC_ADDR=0.0.0.0:9000
ORBITMESH_LOG_LEVEL=info
ORBITMESH_INSTALL_ENDPOINT_URL=https://install.orbitmesh.dev
ORBITMESH_EDGE_RUNTIME_DOWNLOAD_PREFIX=https://downloads.orbitmesh.dev/edge-runtime/latest
ORBITMESH_DEV_SEED_ENABLED=false
Optional production variables:
ORBITMESH_ACCESS_TOKEN_TTL=86400s
ORBITMESH_REDIS_PASSWORD
ORBITMESH_REDIS_URL
ORBITMESH_DEPLOYMENT_TOKEN_TTL=1800s
ORBITMESH_RUNTIME_HEARTBEAT_TIMEOUT=120s
ORBITMESH_RUNTIME_NONCE_TTL=300s
ORBITMESH_DOWNLOADS_DIR=/var/lib/orbitmesh/downloads
Production rules:
ORBITMESH_JWT_SECRETmust be generated and stored as a platform secret.ORBITMESH_DATABASE_DRIVERsupportspgx,postgres,postgresql, andmysql; production defaults should usepgxunless MySQL 8 is intentionally selected.ORBITMESH_DATABASE_URLmust use TLS when the database is not on a private network.- MySQL DSNs must include
parseTime=true; usecharset=utf8mb4and UTC time handling unless the deployment has a stricter standard. - Redis can be configured with
ORBITMESH_REDIS_ADDRandORBITMESH_REDIS_PASSWORD, or with a fullORBITMESH_REDIS_URL. IfORBITMESH_REDIS_URLis set, it takes precedence;ORBITMESH_REDIS_PASSWORDoverrides the password portion of the URL when non-empty. ORBITMESH_PUBLIC_URLmust be the externally reachable API origin.ORBITMESH_DEV_SEED_ENABLEDmust stayfalsefor public production.ORBITMESH_DOWNLOADS_DIRis only a local or development fallback. Production downloads should usedownloads.orbitmesh.dev.
Certificate production variables, required when system certificate automation is enabled:
ORBITMESH_CERTIFICATE_SYSTEM_ENABLED=true
ORBITMESH_CERTIFICATE_SYSTEM_ENDPOINT_DOMAIN_SUFFIX=traffic.edge.orbitmesh.dev
ORBITMESH_CERTIFICATE_SYSTEM_CHALLENGE_TYPE=dns-01
ORBITMESH_CERTIFICATE_SYSTEM_DNS_PROVIDER=cloudflare
ORBITMESH_CERTIFICATE_SYSTEM_KEY_MODE=node_local_csr
ORBITMESH_CERTIFICATE_SYSTEM_RENEW_BEFORE=2592000s
ORBITMESH_CERTIFICATE_SYSTEM_RECONCILE_INTERVAL=300s
ORBITMESH_CERTIFICATE_SYSTEM_RECONCILE_BATCH_SIZE=50
ORBITMESH_ACME_DIRECTORY_URL=https://acme-v02.api.letsencrypt.org/directory
ORBITMESH_ACME_EMAIL=ops@orbitmesh.dev
ORBITMESH_ACME_ACCOUNT_KEY_REF
ORBITMESH_CLOUDFLARE_ZONE_ID
ORBITMESH_CLOUDFLARE_API_TOKEN
Certificate production checklist:
ORBITMESH_ACME_DIRECTORY_URLmust point to the Let's Encrypt production directory before public traffic is enabled. The default config uses the staging directory.ORBITMESH_ACME_EMAILmust be a monitored operations mailbox.ORBITMESH_ACME_ACCOUNT_KEY_REFmust point to a durable file path orfile://mounted secret path.env://VARis supported for temporary environments. Do not store the ACME account key in the database or repository.ORBITMESH_CLOUDFLARE_API_TOKENmust be stored as a platform secret and scoped to the delegated endpoint zone with only the DNS permissions required to create and remove ACME TXT records.ORBITMESH_CLOUDFLARE_ZONE_IDmust be the Cloudflare zone that ownsORBITMESH_CERTIFICATE_SYSTEM_ENDPOINT_DOMAIN_SUFFIX.ORBITMESH_CERTIFICATE_SYSTEM_CHALLENGE_TYPEmust remaindns-01; other challenge types are rejected by the current certificate usecase.ORBITMESH_CERTIFICATE_SYSTEM_KEY_MODEmust remainnode_local_csr; endpoint private keys are generated and kept on the Edge Runtime host.- Edge Runtime hosts must have durable, permission-restricted state storage for
/var/lib/orbitmesh/edge-runtime/certificates. - Certificate readiness must be verified before endpoints are included in subscription output: domain active, certificate issued,
not_afterbeyond the renewal window, and certificate material present on the target Node. - The current Control Plane certificate worker creates ACME order records, waits for Node CSR submission, presents Cloudflare DNS-01 challenges, finalizes issuance, stores certificate material, and updates endpoint readiness. DNS challenge cleanup, renewal scheduling, and tenant custom-domain certificate automation remain follow-up items before public production enablement.
6. Database Migration
Ent owns target schema creation. Breaking model data migrations are explicit SQL and are not implemented as application fallback logic.
Rules:
- CI must not connect to the production database directly.
- do not run development seed in production.
cmd/migratemay remain available for local or manual operator use, but it is not the normal Kubernetes deployment path.- data migrations and corrections must be implemented as explicit SQL or one-off operator commands.
7. Health Checks
HTTP liveness:
GET /healthz
HTTP readiness:
GET /readyz
Expected behavior:
/healthzreturns process liveness./readyzverifies database readiness.- the platform load balancer should use
/readyzfor traffic readiness.
8. Cloudflare DNS
api.orbitmesh.dev should point to the selected container platform origin.
Rules:
- enable HTTPS.
- keep CORS allowed for
https://console.orbitmesh.devandhttps://platform.orbitmesh.dev. - do not proxy gRPC through Cloudflare unless gRPC is explicitly exposed and tested.
- keep
install.orbitmesh.devanddownloads.orbitmesh.devindependent from the API origin.
9. Console Integration
Tenant Console Cloudflare Pages production environment:
NEXT_PUBLIC_ORBITMESH_API_URL=https://api.orbitmesh.dev
Platform Console Cloudflare Pages production environment:
NEXT_PUBLIC_ORBITMESH_API_URL=https://api.orbitmesh.dev
The Control Plane CORS policy must allow:
https://console.orbitmesh.dev
https://platform.orbitmesh.dev
Local development origins may remain enabled:
http://localhost:3000
http://127.0.0.1:3000
10. Release Checklist
Before making api.orbitmesh.dev public:
- Build and publish the Control Plane image with
.github/workflows/release-control-plane.yml. - Provision PostgreSQL or MySQL 8.
- Provision Redis or document the MVP limitation.
- Configure all required environment variables.
- Start
orbitmesh-api; Ent schema creation runs during startup. - Verify
GET /healthz. - Verify
GET /readyz. - Verify Console can call
POST /api/v1/auth/login. - Generate a deployment token from Console.
- Run the install command against
install.orbitmesh.dev. - Verify the Edge Runtime registers and becomes online.
11. Release Status Notes
Current verified production Control Plane:
version: 0.1.79
commit: 12027d2
verified_by: GET /healthz from the production pod
Release note:
api/v0.1.78exists as a tag and its release workflow completed, but it did not become the verified production runtime version.api/v0.1.79is the rollback release that kept the MVP runtime usage principal format asom_sub_<subscription_id>and is the first verified production version after0.1.77.- Runtime usage principal keys are internal accounting identifiers and are distinct from public subscription URL tokens, even though both currently use the
om_sub_namespace.
When recording release history, distinguish between:
- tag pushed.
- image built.
- deployment triggered.
- production pod verified by
/healthz.
Only the last state means the version is considered released to production.
12. Deferred Production Hardening
These are required after MVP validation and before serious production usage:
- Prometheus metrics endpoint and dashboard.
- structured log shipping.
- audit event export.
- rate limiting backed by Redis.
- managed secret rotation.
- database backup and restore drill.
- zero-downtime migration policy.
- API container image publishing pipeline.