Skip to main content

Getting started

platform v0.9.11verified 2026-05-14

This section walks an operator through bringing up a brand-new Delphi deployment. The end goal is a stack that answers calls and serves the dashboard. Each service has its own operations page that documents service-specific knobs once you have a deployment running.

What "a deployment" is

A Delphi deployment is:

  • A set of container images (voiceai-telapi, voiceai-telweb, voiceai-telphi, voiceai-telsys, voiceai-telpro, voiceai-media-server, voiceai-scaler, voiceai-tasker, plus a few upstream images) pinned to a release tag.
  • A set of per-service config bundles (each contains a docker-compose.yaml, an init.sh, a vars.yaml, and any extra service-specific files). The bundles live in an S3 bucket that every host fetches from at boot.
  • A set of runtime variables in AWS SSM Parameter Store (non-sensitive) and AWS Secrets Manager (sensitive), grouped under a NAMESPACE like voiceai/staging or delphi/prod.
  • A set of cloud instances (one per service role) wired together by a private network. Each instance runs a thin cloud-init that places /opt/deployment/.env and /opt/services/<role>/, then runs init.sh.

Everything below is about producing those four things.

The six steps

  1. Prerequisites — accounts, DNS, the S3 config bucket, the container image registry, the namespace.
  2. Configure environment — feed every service's vars.yaml into SSM and Secrets Manager so fetch-env.sh can resolve them at boot.
  3. Provision instances — provider-neutral host requirements: cloud-init, private networking, Docker, IAM, volumes, and load balancers.
  4. Bootstrap and init — what init.sh does on first run: pull config from S3, fetch env from SSM/SM into memory, decode TLS material, pull images, docker compose up.
  5. Verify — follow the smoke checks at the end of Bootstrap and init (every host, dashboard, API through the load balancer).
  6. First use · delphi-setup — on the Web host, after TelWeb's entrypoint finishes Prisma migrate and baseline db seed, run docker compose exec -it voiceai-telweb delphi-setup for registry steps (platform superuser, etc.). Optional: delphi-setup CLI reference for every flag.

Steps 1–5 give you containers that pass health checks and a dashboard that loads; step 6 is what makes the first administrator account and other first-use registry rows land in Postgres. For upgrades, re-run delphi-setup --apply-missing when the release notes say so.

From there, day-2 operations live in the per-service operations pages.

Same shape, different specifics per service

The init.sh path is the same for every service role — that is the whole point of the vars.yaml + fetch-env.sh + init.sh pattern. delphi-setup is not part of init.sh; it is the separate step 6 on the Web host. Each service's init.sh adds its own specifics on top:

ServicePer-service specifics on top of the common flow
DatabaseMounts the data volume; runs prepare-tls-server.sh; creates the OTel monitoring user on first boot.
MediaResolves TLS material in three branches (env-PEM → existing files → self-signed) and writes a CA-for-clients PEM that consumers trust.
TelProResolves TLS via Certbot, Secrets Manager, or self-signed; maps LOG_LEVEL to Kamailio/RTPEngine numeric levels.
VoiceCopies the log-to-span binary into TelSys; brings up Asterisk + TelPhi + optional AudioProc.
APIDecodes the TTS-cache CA bundle into memory; auto-detects PRIVATE_IP from a 10.x interface.
WebTelWeb entrypoint: Prisma migrate deploy + baseline prisma db seed, then Next.js. delphi-setup is run by the operator after boot — see First use. Caddy auto-issues Let's Encrypt for DOMAIN_TELWEB.
SigNozClones the upstream SigNoz repo; converts named volumes to bind mounts; configures redsocks-based transparent proxy via Squid.
SquidBrings up first; no app variables — squid.conf is the configuration surface.
OpsSelects email transport (SMTP or SES via instance profile); leader-elects against Redis.

Foundation services come up first because everything else depends on them:

  1. Squid — every private VM needs an egress proxy.
  2. SigNoz — fixed private IP 10.0.1.10 so every other OTel collector can target it.
  3. Database — Postgres + Redis.
  4. Media — private TLS material has to land in SSM/SM before consumers reference it.
  5. TelPro — public IP and DNS need to settle for Janus WSS.
  6. Web — public IP and DNS need to settle for Let's Encrypt; entrypoint runs migrations + baseline seed, then run delphi-setup from the host.
  7. API — registers behind the managed load balancer.
  8. Voice — joins the Kamailio dispatcher set in Redis as it boots.
  9. Ops — Scaler and Tasker leader-elect against Redis.
  10. Bastion — last, since it knows every other instance's private IP.

Within each service you can re-run init.sh (or update.sh --restart-only) any time after a SSM/SM change.

Next

Continue to Prerequisites.