Build spec and host brief carried in from C:\Claude and WRPS/02-env; the plant model (equipment, tags, alarm bitmask, enums, unit conversions) is derived from WRPS/04-plc/register-map.csv, WRPS/05-scada/modbus/scada-points.csv and WRPS-CTL-003. Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
147 lines
5.1 KiB
YAML
147 lines
5.1 KiB
YAML
# =============================================================================
|
|
# ai-compose.yml -> deployed to ~/ai-compose.yml on yau-sls-poc-lin001
|
|
#
|
|
# House style, inherited from ~/docker-compose.yml (host brief section 7):
|
|
# - restart: unless-stopped on everything
|
|
# - log rotation 10 MB x 3 on everything
|
|
# - NO published host ports: reach services through Caddy on the proxy network
|
|
# - secrets in 0600 env files under ~/ai/, never here and never in Git
|
|
#
|
|
# Orphan-container warnings are expected (shared Compose project name) - ignore.
|
|
#
|
|
# docker compose -f ~/ai-compose.yml up -d
|
|
# =============================================================================
|
|
|
|
services:
|
|
|
|
# ---------------------------------------------------------------------------
|
|
# pg-ai - pgvector, reference data, Cube pre-aggregations.
|
|
# Deliberately NOT on proxy: no UI, nothing outside the AI stack reaches it.
|
|
# Pinned image - do NOT add to Watchtower's update list.
|
|
# ---------------------------------------------------------------------------
|
|
pg-ai:
|
|
image: pgvector/pgvector:pg16
|
|
container_name: pg-ai
|
|
restart: unless-stopped
|
|
networks: [ai-internal]
|
|
env_file:
|
|
- /home/azureuser/ai/pg-ai.env # 0600, not in Git
|
|
environment:
|
|
POSTGRES_DB: plant
|
|
POSTGRES_USER: postgres
|
|
PGDATA: /var/lib/postgresql/data/pgdata
|
|
volumes:
|
|
- /datadisk/pg-ai:/var/lib/postgresql/data
|
|
healthcheck:
|
|
test: ["CMD-SHELL", "pg_isready -U postgres -d plant"]
|
|
interval: 10s
|
|
timeout: 5s
|
|
retries: 5
|
|
logging:
|
|
driver: json-file
|
|
options: { max-size: "10m", max-file: "3" }
|
|
|
|
# ---------------------------------------------------------------------------
|
|
# cube - semantic layer. Reads imh over TDS/1433 with the read-only login, or
|
|
# the fixture tables in pg-ai while USE_FIXTURES=true. Writes pre-aggregations
|
|
# into pg-ai schema cube_preagg. Pinned - not in Watchtower's list.
|
|
# ---------------------------------------------------------------------------
|
|
cube:
|
|
image: cubejs/cube:v1.1.7
|
|
container_name: cube
|
|
restart: unless-stopped
|
|
depends_on:
|
|
pg-ai:
|
|
condition: service_healthy
|
|
networks: [ai-internal, proxy]
|
|
env_file:
|
|
- /home/azureuser/ai/api.env # 0600, not in Git
|
|
environment:
|
|
CUBEJS_DEV_MODE: "false"
|
|
CUBEJS_LOG_LEVEL: warn
|
|
# Pre-aggregation store - always pg-ai, whatever the upstream source is.
|
|
CUBEJS_PRE_AGGREGATIONS_SCHEMA: cube_preagg
|
|
CUBEJS_EXT_DB_TYPE: postgres
|
|
CUBEJS_EXT_DB_HOST: pg-ai
|
|
CUBEJS_EXT_DB_NAME: plant
|
|
CUBEJS_EXT_DB_USER: cube_rw
|
|
# CUBEJS_EXT_DB_PASS, CUBEJS_DB_* and CUBEJS_API_SECRET come from api.env.
|
|
volumes:
|
|
- /home/azureuser/ai/cube/model:/cube/conf/model:ro
|
|
healthcheck:
|
|
test: ["CMD-SHELL", "wget -qO- http://localhost:4000/readyz || exit 1"]
|
|
interval: 30s
|
|
timeout: 5s
|
|
retries: 3
|
|
logging:
|
|
driver: json-file
|
|
options: { max-size: "10m", max-file: "3" }
|
|
|
|
# ---------------------------------------------------------------------------
|
|
# ai-api - FastAPI. Classifier, agent, contracts, guardrails.
|
|
# ---------------------------------------------------------------------------
|
|
ai-api:
|
|
build:
|
|
context: /home/azureuser/ai/api
|
|
dockerfile: Dockerfile
|
|
image: yau/ai-api:local
|
|
container_name: ai-api
|
|
restart: unless-stopped
|
|
depends_on:
|
|
pg-ai:
|
|
condition: service_healthy
|
|
networks: [ai-internal, proxy]
|
|
env_file:
|
|
- /home/azureuser/ai/api.env # 0600, not in Git
|
|
healthcheck:
|
|
test: ["CMD", "python", "-m", "app_healthcheck"]
|
|
interval: 30s
|
|
timeout: 5s
|
|
retries: 3
|
|
logging:
|
|
driver: json-file
|
|
options: { max-size: "10m", max-file: "3" }
|
|
|
|
# ---------------------------------------------------------------------------
|
|
# ai-web - React/Vite build served by nginx. proxy only; the browser talks to
|
|
# the API through its public hostname, so it needs nothing on ai-internal.
|
|
# ---------------------------------------------------------------------------
|
|
ai-web:
|
|
build:
|
|
context: /home/azureuser/ai/web
|
|
dockerfile: Dockerfile
|
|
image: yau/ai-web:local
|
|
container_name: ai-web
|
|
restart: unless-stopped
|
|
networks: [proxy]
|
|
logging:
|
|
driver: json-file
|
|
options: { max-size: "10m", max-file: "3" }
|
|
|
|
# ---------------------------------------------------------------------------
|
|
# ai-ingest - on demand, not a service. Docling -> chunk -> embed -> pg-ai.
|
|
# docker compose -f ~/ai-compose.yml run --rm ai-ingest --all
|
|
# The profile keeps it out of `up -d`.
|
|
# ---------------------------------------------------------------------------
|
|
ai-ingest:
|
|
build:
|
|
context: /home/azureuser/ai/ingest
|
|
dockerfile: Dockerfile
|
|
image: yau/ai-ingest:local
|
|
container_name: ai-ingest
|
|
profiles: [ingest]
|
|
restart: "no"
|
|
networks: [ai-internal]
|
|
env_file:
|
|
- /home/azureuser/ai/api.env # 0600, not in Git
|
|
volumes:
|
|
- /datadisk/ai-docs:/docs:ro
|
|
logging:
|
|
driver: json-file
|
|
options: { max-size: "10m", max-file: "3" }
|
|
|
|
networks:
|
|
ai-internal:
|
|
driver: bridge
|
|
proxy:
|
|
external: true
|