Nomad Zoo
Three chat products, each built the way that kind of chat product is actually built. They share no code and no dependencies — any one of them can be lifted out on its own.
Why three
The two AI chats are the same product built inside out, so the difference between the architectures is visible rather than described.
| Atlas | Relay | |
|---|---|---|
| Transport | Server-Sent Events | WebSocket |
| Language | Python + FastAPI | Node + TypeScript |
| Source of truth | Server | Client |
| History lives in | SQLite on the server | IndexedDB in the browser |
| Cancel is | a separate HTTP request | a frame on the open socket |
| Survives | a page reload, mid-stream | a server restart, mid-conversation |
Try it both ways. In Atlas, run
localStorage.clear() mid-generation and reload — you lose only
which stream was live; every message is intact, because the server is the
truth. In Relay, run ./run.sh restart chat-ws
mid-conversation — the page reconnects with the whole transcript, because
the client never gave it away.