From 18ffe8ddc6865b5e16c8bb650f1fc6b7fd821e5c Mon Sep 17 00:00:00 2001 From: DCCONSTRUCTIONS Date: Thu, 14 May 2026 21:15:05 +0300 Subject: [PATCH] OPS - CODEX AGENTS: product-like Gateway Docker runtime --- .dockerignore | 7 +++++++ Dockerfile | 7 +++++-- README.md | 12 ++++++++++++ docker-compose.local.yml | 27 +++++++++++++++++++++++++-- docker-entrypoint.sh | 8 ++++++++ docs/ARCHITECTURE.md | 1 + docs/IMPLEMENTATION_PLAN.md | 3 ++- 7 files changed, 60 insertions(+), 5 deletions(-) create mode 100644 .dockerignore create mode 100644 docker-entrypoint.sh diff --git a/.dockerignore b/.dockerignore new file mode 100644 index 0000000..2e42280 --- /dev/null +++ b/.dockerignore @@ -0,0 +1,7 @@ +node_modules +dist +.git +.env +npm-debug.log +Dockerfile +docker-compose*.yml diff --git a/Dockerfile b/Dockerfile index 3013e01..6e41dd4 100644 --- a/Dockerfile +++ b/Dockerfile @@ -14,9 +14,12 @@ RUN npm run build FROM node:24-alpine AS runtime WORKDIR /app ENV NODE_ENV=production -COPY --from=deps /app/node_modules ./node_modules +COPY package*.json ./ +RUN npm ci --omit=dev && npm cache clean --force COPY --from=build /app/dist ./dist COPY migrations ./migrations -COPY package*.json ./ +COPY docker-entrypoint.sh ./docker-entrypoint.sh +RUN chmod +x ./docker-entrypoint.sh EXPOSE 4100 +ENTRYPOINT ["./docker-entrypoint.sh"] CMD ["node", "dist/server.js"] diff --git a/README.md b/README.md index 35ac0c0..b86fad4 100644 --- a/README.md +++ b/README.md @@ -37,6 +37,18 @@ All writes go through NODE.DC Agent Gateway, are scoped by agent grants, and are ## Local development +Product-like Docker run: + +```bash +cp .env.example .env +docker compose --env-file .env -f docker-compose.local.yml up -d --build +curl http://127.0.0.1:4100/readyz +``` + +The `agent-gateway` container waits for local Postgres, runs migrations on startup, and exposes the same `:4100` endpoint used by Tasker (`PLANE_NODEDC_AGENT_GATEWAY_URL=http://host.docker.internal:4100`). + +Direct Node.js development: + ```bash cp .env.example .env docker compose --env-file .env -f docker-compose.local.yml up -d postgres diff --git a/docker-compose.local.yml b/docker-compose.local.yml index 8bdf6e3..6e1d538 100644 --- a/docker-compose.local.yml +++ b/docker-compose.local.yml @@ -18,13 +18,36 @@ services: agent-gateway: build: context: . - env_file: - - .env + init: true + environment: + NODE_ENV: ${NODE_ENV:-production} + HOST: 0.0.0.0 + PORT: ${PORT:-4100} + LOG_LEVEL: ${LOG_LEVEL:-info} + DATABASE_URL: postgres://${POSTGRES_USER:-nodedc_agent_gateway}:${POSTGRES_PASSWORD:-replace-with-local-postgres-password}@postgres:5432/${POSTGRES_DB:-nodedc_agent_gateway} + NODEDC_AGENT_GATEWAY_PUBLIC_URL: ${NODEDC_AGENT_GATEWAY_PUBLIC_URL:-http://localhost:4100} + NODEDC_AGENT_GATEWAY_INTERNAL_TOKEN: ${NODEDC_AGENT_GATEWAY_INTERNAL_TOKEN:-local-dev-codex-agent-gateway-token-change-me} + NODEDC_LAUNCHER_INTERNAL_URL: ${NODEDC_LAUNCHER_INTERNAL_URL:-http://launcher.local.nodedc} + NODEDC_TASKER_INTERNAL_URL: ${NODEDC_TASKER_INTERNAL_URL:-http://task.local.nodedc} + NODEDC_INTERNAL_ACCESS_TOKEN: ${NODEDC_INTERNAL_ACCESS_TOKEN:-local-dev-nodedc-internal-token-change-me} depends_on: postgres: condition: service_healthy + extra_hosts: + - "auth.local.nodedc:host-gateway" + - "launcher.local.nodedc:host-gateway" + - "task.local.nodedc:host-gateway" ports: - "${PORT:-4100}:${PORT:-4100}" + healthcheck: + test: + [ + "CMD-SHELL", + "node -e \"fetch('http://127.0.0.1:' + (process.env.PORT || 4100) + '/readyz').then(async r => { const b = await r.json(); process.exit(r.ok && b.ok ? 0 : 1); }).catch(() => process.exit(1))\"", + ] + interval: 10s + timeout: 5s + retries: 10 volumes: agent-gateway-postgres: diff --git a/docker-entrypoint.sh b/docker-entrypoint.sh new file mode 100644 index 0000000..030a050 --- /dev/null +++ b/docker-entrypoint.sh @@ -0,0 +1,8 @@ +#!/bin/sh +set -e + +if [ "${NODEDC_AGENT_GATEWAY_SKIP_MIGRATIONS:-0}" != "1" ]; then + npm run migrate:dist +fi + +exec "$@" diff --git a/docs/ARCHITECTURE.md b/docs/ARCHITECTURE.md index e1f21d9..d68f67e 100644 --- a/docs/ARCHITECTURE.md +++ b/docs/ARCHITECTURE.md @@ -264,5 +264,6 @@ The service should support: - staging `.env.staging`; - production secret store; - Docker image build; +- container startup migrations; - health endpoint; - preflight script validating URLs/secrets. diff --git a/docs/IMPLEMENTATION_PLAN.md b/docs/IMPLEMENTATION_PLAN.md index bd7be5d..7d30fb9 100644 --- a/docs/IMPLEMENTATION_PLAN.md +++ b/docs/IMPLEMENTATION_PLAN.md @@ -23,12 +23,13 @@ Exit criteria: ## Phase 1. Agent Gateway skeleton -Status: done in `e95cb3a`, `112522c`, `14c5f49`, `9f40207`, and the MCP transport slice. Initial service, migrations, persistence endpoints, token hashing, bearer-token session auth, product tool endpoints, local Postgres compose, and Gateway smoke checks are implemented. +Status: done in `e95cb3a`, `112522c`, `14c5f49`, `9f40207`, and the MCP transport slice. Initial service, migrations, persistence endpoints, token hashing, bearer-token session auth, product tool endpoints, local Postgres compose, product-like Gateway container startup, and Gateway smoke checks are implemented. Create standalone service with: - Dockerfile; - compose for local dev; +- container entrypoint that runs migrations before service startup; - health endpoint; - env validation; - database migrations;