From a5e8890df215bb71fc996348f64361b66ab49c32 Mon Sep 17 00:00:00 2001 From: root Date: Sat, 14 Mar 2026 05:24:01 +0000 Subject: [PATCH] Add Cosmos emulator prototype support --- .env.example | 12 ++++++---- .gitignore | 1 + README.md | 2 ++ docker-compose.yml | 36 +++++++++++++++++++++++++++- docs/PROTOTYPE_DEPLOYMENT.md | 16 +++++++------ packages/cosmos/src/containers.ts | 1 + packages/storage/package.json | 7 +----- scripts/prototype-up.sh | 1 - services/platform-service/Dockerfile | 3 +++ 9 files changed, 59 insertions(+), 20 deletions(-) diff --git a/.env.example b/.env.example index d57ea7a2..a39a3251 100644 --- a/.env.example +++ b/.env.example @@ -3,15 +3,17 @@ # ── Azure Key Vault (optional — secrets fall back to env vars) ─ # Set this to resolve secrets from AKV instead of .env: -AZURE_KEYVAULT_URL=https://kv-mywisprai.vault.azure.net +AZURE_KEYVAULT_URL= -# ── Azure Cosmos DB ──────────────────────────────────────────── -COSMOS_ENDPOINT=https://cosmos-mywisprai.documents.azure.com:443/ -COSMOS_KEY=your-cosmos-key +# ── Cosmos DB (prototype defaults to local emulator) ─────────── +# For the Docker prototype stack, leave these pointed at the local emulator. +# When you move to a managed environment later, replace them with real Azure values. +COSMOS_ENDPOINT=http://cosmos-emulator:8081 +COSMOS_KEY=C2y6yDjf5/R+ob0N8A7Cgv30VRDJIWEHLM+4QDU5DE2nQ9nDuVTqobD4b8mGGyPMbIZnqyMsEcaGQy67XIw/Jw== COSMOS_DATABASE=lysnrai # ── Auth (platform-service) ───────────────────────── -JWT_SECRET=your-jwt-secret +JWT_SECRET=change-me-prototype-jwt-secret # ── Azure Blob Storage (platform-service) ───────────────────── AZURE_BLOB_CONNECTION_STRING= diff --git a/.gitignore b/.gitignore index d7696fdf..651cf202 100644 --- a/.gitignore +++ b/.gitignore @@ -6,6 +6,7 @@ coverage/ # Env / Secrets .env +.env.bak .env.local .env.*.local *.pem diff --git a/README.md b/README.md index 955e1154..816c0ef1 100644 --- a/README.md +++ b/README.md @@ -42,6 +42,8 @@ cp .env.example .env See [docs/PROTOTYPE_DEPLOYMENT.md](docs/PROTOTYPE_DEPLOYMENT.md) for the required environment variables and day-to-day commands. +The prototype stack now includes a local Cosmos DB Emulator container, so the default `.env.example` values are wired for single-VM Docker use. + ## Current Capability Surface - **Shared packages** — 36 `@bytelyst/*` packages covering auth, config, API clients, storage, sync, telemetry, diagnostics, design tokens, SDK support, and testing. diff --git a/docker-compose.yml b/docker-compose.yml index b9ad8f5c..59f26deb 100644 --- a/docker-compose.yml +++ b/docker-compose.yml @@ -1,4 +1,26 @@ services: + # ── Azure Cosmos DB Emulator (prototype only) ───────────────── + cosmos-emulator: + image: mcr.microsoft.com/cosmosdb/linux/azure-cosmos-emulator:vnext-preview + ports: + - '8081:8081' + - '1234:1234' + environment: + - PROTOCOL=http + - ENABLE_EXPLORER=true + - GATEWAY_PUBLIC_ENDPOINT=cosmos-emulator + healthcheck: + test: + [ + 'CMD-SHELL', + 'bash -lc ''exec 3<>/dev/tcp/127.0.0.1/8080; printf "GET /ready HTTP/1.1\r\nHost: localhost\r\nConnection: close\r\n\r\n" >&3; grep -q "200 OK" <&3''', + ] + interval: 10s + timeout: 5s + retries: 12 + start_period: 20s + restart: unless-stopped + # ── Loki (Log Aggregation) ──────────────────────────────────── loki: image: grafana/loki:3.3.2 @@ -74,6 +96,9 @@ services: - PORT=4003 # Local/dev convenience: ensure Cosmos DB + containers exist. - COSMOS_AUTO_INIT=true + depends_on: + cosmos-emulator: + condition: service_healthy labels: - 'traefik.enable=true' - 'traefik.http.routers.platform.rule=PathPrefix(`/api`) || PathPrefix(`/public`) || PathPrefix(`/health`)' @@ -97,13 +122,22 @@ services: environment: - PORT=4005 - PYTHON_SIDECAR_URL=http://localhost:4006 + depends_on: + cosmos-emulator: + condition: service_healthy labels: - 'traefik.enable=true' - 'traefik.http.routers.extraction.rule=PathPrefix(`/api/extract`) || PathPrefix(`/api/tasks`)' - 'traefik.http.services.extraction.loadbalancer.server.port=4005' restart: unless-stopped healthcheck: - test: ['CMD', 'wget', '-q', '--spider', 'http://127.0.0.1:4005/health'] + test: + [ + 'CMD', + 'node', + '-e', + 'fetch("http://127.0.0.1:4005/health").then(r => process.exit(r.ok ? 0 : 1)).catch(() => process.exit(1))', + ] interval: 30s timeout: 10s retries: 3 diff --git a/docs/PROTOTYPE_DEPLOYMENT.md b/docs/PROTOTYPE_DEPLOYMENT.md index da390de7..30fd0330 100644 --- a/docs/PROTOTYPE_DEPLOYMENT.md +++ b/docs/PROTOTYPE_DEPLOYMENT.md @@ -7,17 +7,17 @@ This repo is currently set up to run as a single-host prototype with Docker Comp - `platform-service` - `extraction-service` - `mcp-server` +- `cosmos-emulator` - `gateway` (Traefik) - `loki` - `grafana` ## What Stays External -- Azure Cosmos DB - Azure Key Vault if you choose to use it - Any real API credentials such as Stripe or Gemini -For the prototype phase, keep secrets in `.env` and keep state in managed external services rather than adding more local containers. +For this VM prototype, Cosmos is self-hosted through the Linux Cosmos DB Emulator container. Everything else should still stay in `.env` and move to a real secret manager later. ## First-Time Setup @@ -27,8 +27,6 @@ cp .env.example .env Fill in at least: -- `COSMOS_ENDPOINT` -- `COSMOS_KEY` - `JWT_SECRET` If you want extraction features that call Gemini, also set: @@ -44,8 +42,8 @@ If you want extraction features that call Gemini, also set: That script will: 1. Validate the required environment variables. -2. Build the shared packages needed by the Docker images. -3. Build and start the Compose stack. +2. Start the local Cosmos DB emulator. +3. Build and start the rest of the Compose stack. ## Day-To-Day Commands @@ -54,11 +52,15 @@ docker compose ps docker compose logs -f platform-service docker compose logs -f extraction-service docker compose logs -f mcp-server +docker compose logs -f cosmos-emulator docker compose down ``` +The Cosmos Data Explorer is exposed on `http://localhost:1234`. + ## Notes - This is intended for early prototype use on a single machine. - Do not commit `.env`. -- When the project moves to a more secure environment later, keep the same service boundaries and move secrets out of `.env` into a proper secret manager. +- The Linux emulator is a preview and is only appropriate for local or prototype use. +- When the project moves to a more secure environment later, replace the emulator with a real Azure Cosmos DB account and move secrets out of `.env` into a proper secret manager. diff --git a/packages/cosmos/src/containers.ts b/packages/cosmos/src/containers.ts index 943aa37e..acd009d2 100644 --- a/packages/cosmos/src/containers.ts +++ b/packages/cosmos/src/containers.ts @@ -92,6 +92,7 @@ async function createContainerSafe( id: name, partitionKey: { paths: [config.partitionKeyPath], + kind: 'Hash', } as PartitionKeyDefinition, ...(config.defaultTtl != null && { defaultTtl: config.defaultTtl }), }; diff --git a/packages/storage/package.json b/packages/storage/package.json index fd04dd11..bca26f2d 100644 --- a/packages/storage/package.json +++ b/packages/storage/package.json @@ -21,14 +21,9 @@ "build": "tsc", "test": "vitest run" }, - "peerDependencies": { + "dependencies": { "@azure/storage-blob": ">=12.0.0" }, - "peerDependenciesMeta": { - "@azure/storage-blob": { - "optional": true - } - }, "devDependencies": { "vitest": "^3.0.0" } diff --git a/scripts/prototype-up.sh b/scripts/prototype-up.sh index 02462904..bc96051d 100755 --- a/scripts/prototype-up.sh +++ b/scripts/prototype-up.sh @@ -11,7 +11,6 @@ if [[ ! -f .env ]]; then fi "$REPO_ROOT/scripts/check-prototype-env.sh" "$REPO_ROOT/.env" -"$REPO_ROOT/scripts/docker-prep.sh" echo "Starting prototype stack with Docker Compose..." docker compose up -d --build diff --git a/services/platform-service/Dockerfile b/services/platform-service/Dockerfile index 4492d9ec..52bbcde0 100644 --- a/services/platform-service/Dockerfile +++ b/services/platform-service/Dockerfile @@ -13,11 +13,14 @@ COPY packages/blob/package.json packages/blob/ COPY packages/config/package.json packages/config/ COPY packages/auth/package.json packages/auth/ COPY packages/api-client/package.json packages/api-client/ +COPY packages/datastore/package.json packages/datastore/ +COPY packages/events/package.json packages/events/ COPY packages/fastify-core/package.json packages/fastify-core/ COPY packages/logger/package.json packages/logger/ COPY packages/monitoring/package.json packages/monitoring/ COPY packages/react-auth/package.json packages/react-auth/ COPY packages/design-tokens/package.json packages/design-tokens/ +COPY packages/storage/package.json packages/storage/ COPY packages/testing/package.json packages/testing/ COPY services/platform-service/package.json services/platform-service/