Repository navigation
deployment
Active contributors: Rom Iluz
How Memongo runs locally, in CI, and in production — Docker Compose for development, a multi-stage Dockerfile for the API, GitHub Actions for quality/e2e gates and npm publishing, and Cloudflare Workers for the web console. For the app's internal request-handling architecture see API app; for the wire API see API.
Two compose layouts exist for different purposes:
-
docker/docker-compose.yml— the original one-command setup: a singlemongodb/mongodb-atlas-local:previewcontainer (mongod + mongot, Atlas Search + Vector Search, auto-embeddings via Voyage AI whenVOYAGE_API_KEYis set), bound to127.0.0.1only. Run withdocker compose -f docker/docker-compose.yml up -d. -
docker/compose.yaml+docker/compose.override.yaml— a split base/override pair.compose.yamlalone defines only theapiservice and is production-safe (no local database, expects an externalMEMONGO_MONGODB_URI). Running plaindocker composefromdocker/auto-mergescompose.override.yaml, which adds the localmongodbservice (Atlas Local, pinned dated tag8.2.6-20260715T144108Z) and makesapiwait on its healthcheck (depends_on: condition: service_healthy).
Both Mongo services publish 27017 on loopback only and use the Atlas Local image's built-in runner healthcheck command (verifies mongod and mongot together), never a plain mongo:7 image — auto-embedding needs mongot.
compose.yaml fails closed on a missing admin token: MEMONGO_API_KEY=${MEMONGO_API_KEY:?set MEMONGO_API_KEY} aborts compose startup rather than booting an unauthenticated API.
apps/api/Dockerfile is a three-stage build:
-
prepare(node:22-slim+turbo prune --docker @memongo/api) — extracts onlyapps/apiand its workspace dependencies (@memongo/memory-bridge,@memongo/memory-engine,@memongo/lib) from the monorepo. -
installer(oven/bun:1-debian) —bun install --frozen-lockfileagainst the pruned lockfile, thenbun run turbo build --filter=@memongo/api.... The roottsconfig.base.jsonis copied explicitly becauseturbo prune'sout/full/omits root-level config files. -
runner(node:22-slim) — copies onlydist/,package.jsonfiles,packages/, andnode_modules/into a non-root (USER node) runtime image, and runs the built JS directly with plainnode(notsx, no TypeScript at runtime).
The final image binds MEMONGO_API_HOST=0.0.0.0 (required inside a container; the process defaults to loopback otherwise) and MEMONGO_API_PORT=3847, and declares a HEALTHCHECK that curls /ready via node -e "fetch(...)" — no extra curl/wget binary needed in the slim image. apps/api/.dockerignore excludes apps/web, apps/docs, apps/mcp, benchmarks, and markdown files from the build context to keep it small.
.github/workflows/ci.yml runs on every pull request and push to main, with two jobs:
flowchart LR
A[quality job] -->|typecheck, lint, build,\ncheck-publishability, test| B((green))
C[e2e job] -->|spin up mongodb-atlas-local\nservice container| D[bun run test:e2e:tier-a]
D --> B
-
quality—bun install --frozen-lockfile, thenbun run check-types,bun run lint,bun run build,bun run check-publishability(the same publish gate described indocs/platform/publish.md), andbun run test. -
e2e— starts amongodb/mongodb-atlas-local:previewservice container (same image as local dev), waits on itsrunner healthcheck, builds, then runsbun run --filter @memongo/memory-engine test:e2e:tier-aagainstmongodb://127.0.0.1:27017/?directConnection=true. Tier A is scoped to paths that need only MongoDB — transactions, indexes, tenant isolation, background jobs — so every PR is gated without requiring any secret.
.github/workflows/e2e-nightly.yml runs on a 0 3 * * * cron (plus manual dispatch) and extends tier A with the paths that need external model access: the Mongo service container is given VOYAGE_API_KEY directly (auto-embeddings are served by mongot inside the container, so the key must be present there, not just in the test process), and the job runs bun run --filter @memongo/memory-engine test:e2e — the full suite, covering auto-embedding search quality and LLM-assisted extraction/enrichment (MEMONGO_ENRICHMENT_MODEL). A 60-minute timeout bounds the job.
.github/workflows/publish.yml triggers on a v* git tag push or manual dispatch. It installs with Bun, builds, runs the full test suite and check-publishability again (belt-and-suspenders with CI), then loops over the coordinated package list — packages/lib, memory-engine, memory-bridge, memongo-memory, client, tools, pi-extension, apps/mcp — publishing each with npm publish --access public --provenance using an NPM_TOKEN secret. A package marked private: true in this loop is treated as a hard failure (exit 1), not a silent skip. See docs/platform/publish.md for the full release checklist, version-sync rules across apps/api/src/version.ts / apps/mcp/src/version.ts / packages/client/src/version.ts, and the recommended dependency-ordered publish sequence.
.github/workflows/droid-wiki-refresh.yml runs on every push to main (plus manual dispatch): it installs the Factory Droid CLI, configures a Grove-hosted Claude Sonnet model via ~/.factory/settings.json, and runs droid exec "/wiki" to regenerate this wiki and commit it back to the repo.
apps/web (Next.js) deploys to Cloudflare Workers through OpenNext:
-
apps/web/open-next.config.tsusesdefineCloudflareConfig()with no overrides — the default OpenNext-for-Cloudflare adapter behavior. -
apps/web/wrangler.jsoncpoints Workers at the OpenNext build output (main: ".open-next/worker.js", static assets from.open-next/assets), enablesnodejs_compatandglobal_fetch_strictly_publiccompatibility flags, binds aWORKER_SELF_REFERENCEservice to itself (the standard OpenNext pattern for Cloudflare's incremental static regeneration/revalidation callbacks), and turns on Workers observability.
docs/platform/self-host.md is the canonical self-host runbook — read it in full before a production deployment. In summary: run MongoDB (managed Atlas cloud, or the Atlas Local Preview image for reproducibility), run apps/api as a stateless process or container behind your own TLS-terminating ingress, and optionally run apps/web and apps/mcp. Required/notable configuration: MEMONGO_MONGODB_URI, MEMONGO_API_KEY (mandatory on any untrusted network), MEMONGO_API_SCOPED_KEYS for narrower agent-facing tokens (see Security and Multi-tenancy and scopes), and VOYAGE_API_KEY for auto-embed/hybrid retrieval quality. Liveness/readiness/status checks are GET /health, GET /ready, and GET /v1/status respectively (API has the full route reference).