services:
  dashboard:
    image: fonoster/dashboard:0.15.15
    restart: unless-stopped
    ports:
      - 3030
    environment:
      - SERVER_DASHBOARD_SESSION_SECRET=${SERVER_DASHBOARD_SESSION_SECRET}

  apiserver:
    image: fonoster/apiserver:0.15.15
    restart: unless-stopped
    depends_on:
      postgres:
        condition: service_healthy
    environment:
      - APISERVER_APP_URL=${APISERVER_APP_URL}
      - APISERVER_ASTERISK_ARI_PROXY_URL=${APISERVER_ASTERISK_ARI_PROXY_URL}
      - APISERVER_ASTERISK_ARI_SECRET=${APISERVER_ASTERISK_ARI_SECRET}
      - APISERVER_ASTERISK_ARI_USERNAME=${APISERVER_ASTERISK_ARI_USERNAME}
      - APISERVER_AUTHZ_SERVICE_ENABLED=${APISERVER_AUTHZ_SERVICE_ENABLED}
      - APISERVER_AUTHZ_SERVICE_HOST=${APISERVER_AUTHZ_SERVICE_HOST}
      - APISERVER_AUTHZ_SERVICE_METHODS=${APISERVER_AUTHZ_SERVICE_METHODS}
      - APISERVER_AUTHZ_SERVICE_PORT=${APISERVER_AUTHZ_SERVICE_PORT}
      - APISERVER_CLOAK_ENCRYPTION_KEY=${APISERVER_CLOAK_ENCRYPTION_KEY}
      - APISERVER_DATABASE_URL=${APISERVER_DATABASE_URL}
      - APISERVER_IDENTITY_DATABASE_URL=${APISERVER_IDENTITY_DATABASE_URL}
      - APISERVER_IDENTITY_ISSUER=${APISERVER_IDENTITY_ISSUER}
      - APISERVER_IDENTITY_CONTACT_VERIFICATION_REQUIRED=${APISERVER_IDENTITY_CONTACT_VERIFICATION_REQUIRED}
      - APISERVER_IDENTITY_TWO_FACTOR_AUTHENTICATION_REQUIRED=${APISERVER_IDENTITY_TWO_FACTOR_AUTHENTICATION_REQUIRED}
      - APISERVER_IDENTITY_WORKSPACE_INVITE_EXPIRATION=${APISERVER_IDENTITY_WORKSPACE_INVITE_EXPIRATION}
      - APISERVER_IDENTITY_WORKSPACE_INVITE_FAIL_URL=${APISERVER_IDENTITY_WORKSPACE_INVITE_FAIL_URL}
      - APISERVER_IDENTITY_WORKSPACE_INVITE_URL=${APISERVER_IDENTITY_WORKSPACE_INVITE_URL}
      - APISERVER_IDENTITY_OAUTH2_GITHUB_CLIENT_ID=${APISERVER_IDENTITY_OAUTH2_GITHUB_CLIENT_ID}
      - APISERVER_IDENTITY_OAUTH2_GITHUB_CLIENT_SECRET=${APISERVER_IDENTITY_OAUTH2_GITHUB_CLIENT_SECRET}
      - APISERVER_IDENTITY_OAUTH2_GITHUB_ENABLED=${APISERVER_IDENTITY_OAUTH2_GITHUB_ENABLED}
      - APISERVER_INFLUXDB_INIT_ORG=${APISERVER_INFLUXDB_INIT_ORG}
      - APISERVER_INFLUXDB_INIT_PASSWORD=${APISERVER_INFLUXDB_INIT_PASSWORD}
      - APISERVER_INFLUXDB_INIT_TOKEN=${APISERVER_INFLUXDB_INIT_TOKEN}
      - APISERVER_INFLUXDB_INIT_USERNAME=${APISERVER_INFLUXDB_INIT_USERNAME}
      - APISERVER_INFLUXDB_URL=${APISERVER_INFLUXDB_URL}
      - APISERVER_LOGS_FORMAT=${APISERVER_LOGS_FORMAT}
      - APISERVER_LOGS_LEVEL=${APISERVER_LOGS_LEVEL}
      - APISERVER_LOGS_TRANSPORT=${APISERVER_LOGS_TRANSPORT}
      - APISERVER_NATS_URL=${APISERVER_NATS_URL}
      - APISERVER_OWNER_EMAIL=${APISERVER_OWNER_EMAIL}
      - APISERVER_OWNER_NAME=${APISERVER_OWNER_NAME}
      - APISERVER_OWNER_PASSWORD=${APISERVER_OWNER_PASSWORD}
      - APISERVER_ROOT_DOMAIN=${APISERVER_ROOT_DOMAIN}
      - APISERVER_SMTP_AUTH_PASS=${APISERVER_SMTP_AUTH_PASS}
      - APISERVER_SMTP_AUTH_USER=${APISERVER_SMTP_AUTH_USER}
      - APISERVER_SMTP_HOST=${APISERVER_SMTP_HOST}
      - APISERVER_SMTP_PORT=${APISERVER_SMTP_PORT}
      - APISERVER_SMTP_SECURE=${APISERVER_SMTP_SECURE}
      - APISERVER_SMTP_SENDER=${APISERVER_SMTP_SENDER}
      - APISERVER_SIGNALING_SERVER=${APISERVER_SIGNALING_SERVER}
      - APISERVER_TWILIO_ACCOUNT_SID=${APISERVER_TWILIO_ACCOUNT_SID}
      - APISERVER_TWILIO_AUTH_TOKEN=${APISERVER_TWILIO_AUTH_TOKEN}
      - APISERVER_TWILIO_PHONE_NUMBER=${APISERVER_TWILIO_PHONE_NUMBER}
    expose:
      - 50051
    volumes:
      - ../files/config/keys:/opt/fonoster/keys:ro
      - ../files/config/integrations.json:/opt/fonoster/integrations.json:ro

  autopilot:
    image: fonoster/autopilot:0.15.15
    restart: unless-stopped
    expose:
      - 50061
    environment:
      - AUTOPILOT_AWS_S3_ACCESS_KEY_ID=${AUTOPILOT_AWS_S3_ACCESS_KEY_ID}
      - AUTOPILOT_AWS_S3_ENDPOINT=${AUTOPILOT_AWS_S3_ENDPOINT}
      - AUTOPILOT_AWS_S3_REGION=${AUTOPILOT_AWS_S3_REGION}
      - AUTOPILOT_AWS_S3_SECRET_ACCESS_KEY=${AUTOPILOT_AWS_S3_SECRET_ACCESS_KEY}
      - AUTOPILOT_CONVERSATION_PROVIDER=${AUTOPILOT_CONVERSATION_PROVIDER}
      - AUTOPILOT_KNOWLEDGE_BASE_ENABLED=${AUTOPILOT_KNOWLEDGE_BASE_ENABLED}
      - AUTOPILOT_LOGS_FORMAT=${AUTOPILOT_LOGS_FORMAT}
      - AUTOPILOT_LOGS_LEVEL=${AUTOPILOT_LOGS_LEVEL}
      - AUTOPILOT_LOGS_TRANSPORT=${AUTOPILOT_LOGS_TRANSPORT}
      - AUTOPILOT_OPENAI_API_KEY=${AUTOPILOT_OPENAI_API_KEY}
      - AUTOPILOT_UNSTRUCTURED_API_KEY=${AUTOPILOT_UNSTRUCTURED_API_KEY}
      - AUTOPILOT_UNSTRUCTURED_API_URL=${AUTOPILOT_UNSTRUCTURED_API_URL}
    volumes:
      - ../files/config/integrations.json:/opt/fonoster/integrations.json:ro

  routr:
    image: fonoster/routr-one:2.13.13
    restart: unless-stopped
    depends_on:
      postgres:
        condition: service_healthy
    environment:
      DATABASE_URL: ${ROUTR_DATABASE_URL}
      EXTERNAL_ADDRS: ${ROUTR_EXTERNAL_ADDRS}
      LOGS_FORMAT: ${ROUTR_LOGS_FORMAT}
      LOGS_LEVEL: ${ROUTR_LOGS_LEVEL}
      LOGS_TRANSPORT: ${ROUTR_LOGS_TRANSPORT}
      NATS_PUBLISHER_ENABLED: "true"
      NATS_PUBLISHER_URL: ${ROUTR_NATS_PUBLISHER_URL}
      RTPENGINE_HOST: ${ROUTR_RTPENGINE_HOST}
      START_INTERNAL_DB: "false"
      CONNECT_VERIFIER_PUBLIC_KEY_PATH: /etc/routr/keys/public.pem
    expose:
      - 51907
      - 51908
    ports:
      - 5060:5060/udp
      - 5060-5063:5060-5063
    volumes:
      - ../files/config/keys/public.pem:/etc/routr/keys/public.pem

  # RTPEngine uses a range of ports to handle RTP traffic. Because exposing a large range of ports 
  # is not possible in Docker, we need to use network_mode: host.
  #
  # Unfortunately, network_mode: host is not supported for Windows or Mac.
  # In those cases, we need to use a different approach.
  #
  # By default we are opening a small range of ports (10000-10100) to handle RTP traffic.
  # However, this is not enough for production environments.
  #
  # We recommend that when using Linux you use network_mode: host and remove the ports section.
  rtpengine:
    image: fonoster/rtpengine:0.3.17
    restart: unless-stopped
    platform: linux/x86_64
    ports: 
      - 10000-10100:10000-10100/udp
      - 8080:8080
    environment:
      PORT_MAX: ${RTPENGINE_PORT_MAX}
      PORT_MIN: ${RTPENGINE_PORT_MIN}
      PUBLIC_IP: ${RTPENGINE_PUBLIC_IP}

  asterisk:
    image: fonoster/asterisk:20
    restart: unless-stopped
    environment:
      ARI_PROXY_URL: ${ASTERISK_ARI_PROXY_URL}
      ARI_SECRET: ${ASTERISK_ARI_SECRET}
      ARI_USERNAME: ${ASTERISK_ARI_USERNAME}
      CODECS: ${ASTERISK_CODECS}
      DTMF_MODE: ${ASTERISK_DTMF_MODE}
      RTP_PORT_END: ${ASTERISK_RTP_PORT_END}
      RTP_PORT_START: ${ASTERISK_RTP_PORT_START}
      SIPPROXY_HOST: ${ASTERISK_SIPPROXY_HOST}
      SIPPROXY_PORT: ${ASTERISK_SIPPROXY_PORT}
      SIPPROXY_SECRET: ${ASTERISK_SIPPROXY_SECRET}
      SIPPROXY_USERNAME: ${ASTERISK_SIPPROXY_USERNAME}
    expose:
      - 6060

  postgres:
    image: postgres:16.10-alpine3.22
    restart: unless-stopped
    environment:
      PGTZ: UTC
      POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
      POSTGRES_USER: ${POSTGRES_USER}
      POSTGRES_DB: ${POSTGRES_DB}
      TZ: UTC
    expose:
      - 5432
    volumes:
      - db:/var/lib/postgresql/data
      - ../files/config/init-db.sh:/docker-entrypoint-initdb.d/init-db.sh:ro
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U ${POSTGRES_USER} -d ${POSTGRES_DB}"]
      interval: 5s
      timeout: 5s
      retries: 10

  influxdb:
    image: influxdb:2.7
    restart: unless-stopped
    expose:
      - 8086
    environment:
      DOCKER_INFLUXDB_INIT_ADMIN_TOKEN: ${INFLUXDB_INIT_TOKEN}
      DOCKER_INFLUXDB_INIT_BUCKET: calls
      DOCKER_INFLUXDB_INIT_MODE: setup
      DOCKER_INFLUXDB_INIT_ORG: ${INFLUXDB_INIT_ORG}
      DOCKER_INFLUXDB_INIT_PASSWORD: ${INFLUXDB_INIT_PASSWORD}
      DOCKER_INFLUXDB_INIT_USERNAME: ${INFLUXDB_INIT_USERNAME}
    volumes:
      - influxdb:/var/lib/influxdb2

  nats:
    image: nats:2.11.8
    restart: unless-stopped
    expose:
      - 4222

  envoy:
    image: envoyproxy/envoy:v1.35.0
    restart: unless-stopped
    command: ["/usr/local/bin/envoy", "-c", "/etc/envoy/envoy.yaml"]
    volumes:
      - ../files/config:/etc/envoy:ro
    ports:
      - 8449:8449

volumes:
  db:
  influxdb:

