Loading docs/architecture.md…
Architecture
A cart written in free text leaves the browser, goes through the BFF, then through the API, which reads it in seven stages, two of them side by side. The models read, through OpenRouter; the code counts and sets the price; every request leaves a trace in Langfuse.
Open the stack diagram (Claude artifact)
api/openapi.yamlWhat POST /v1/quotes does with example 5 of the brief: the three volumes and La chèvre. Every stage may refuse the cart with a stable code; the models never set an amount.
count), and the worst score decides. The recount never sets the price. An injection that got past the guard could at worst misfile a title among four options: it never reaches the amount.| Layer | Technologies | Role |
|---|---|---|
| Contract | OpenAPI 3.1 oapi-codegen 2.8 openapi-typescript 7 | The source of truth. The Go server and the web and e2e types are generated from it; CI refuses any drift. Every word put to a model lives in prompts/, shared the same way. |
| Web | Next.js 16.3 React 19.3 iron-session 9 openapi-fetch CSS Modules | The UI and the BFF: the session, the quoter picked by name, one French message per refusal. |
| Go API | Go 1.26 net/http log/slog o200k_base, O(n log n) merge | The pipeline, pricing in cents, RFC 9457 errors. The tokenizer is compiled in: counting needs no network. |
| TypeScript API | Node 26 Hono openai Ajv js-tiktoken ranks | The same pipeline on Node, run from its .ts files with no build step. Every model answer is checked against the schema. |
| Python API | Python 3.14 uv FastAPI httpx openai tiktoken mypy --strict | The same pipeline on asyncio. The tokenizer's vocabulary is fetched once against a pinned checksum, and never at runtime. |
| Agents and models | trpc-agent-go 1.11.2 OpenRouter Jev 1.13 GPT-6 Luna DeepSeek V4.1 Flash | Jev decides (guard, identify, judge); Luna extracts under a strict schema and DeepSeek recounts with the same prompt; trpc-agent-go carries the agent, the traces and the evaluation. |
| Observability | Langfuse 4 OpenTelemetry Postgres 17 ClickHouse 25.12 Redis 7 MinIO | One trace per request, one span per stage; the benches keep their datasets and experiments there. |
| Tests and benches | go test -race pytest Vitest 5 Testing Library Ajv 2020-12 | Deterministic fake engines in CI; live benches only with RUN_LIVE=1. |
| Tooling | Task Docker Compose GitHub Actions golangci-lint 2 ESLint Prettier | One command per gesture: task ci, task e2e, task langfuse:up, task bench, task docs. |
Loading docs/architecture.md…