Skip to content

Architecture

diegokoes edited this page Jul 5, 2026 · 2 revisions

Architecture

   MCP client (Claude Code, Codex CLI, ...) --(MCP stdio)--> tachý MCP server ─┐
                                                                               │
   teammates / cron / CI --------------------(HTTP)--------> Hono REST API ────┼─> core ─> Postgres
                                                                               │            │
                                                          packages/sources/* <─┘            │
                                                          (Freshdesk, GitHub) ──────────────┘

core is source-agnostic and holds all the logic. mcp, api, and cli are thin entrypoints that wire core to a way of calling it. sources/* are pluggable adapters behind a single interface, so adding a source means writing one adapter, with no schema or core changes.

The core is LLM-agnostic

The stack is LLM-agnostic at its core. packages/mcp exposes the tools over the Model Context Protocol and packages/core is pure domain logic plus Postgres. No LLM provider is hardcoded on this path. Any MCP-capable host (Claude Code, another vendor's client, or an organization's own model) can drive the tools.

The only Claude-specific component is the optional bundled server-side agent, which powers the web Chat. It lives in one file and is consumed by one route. Everything else, including the entire MCP and REST surface, is provider-neutral.

Entrypoints

Entrypoint Package Transport Who calls it
MCP server packages/mcp stdio (MCP) local agents, any MCP client
REST API packages/api HTTP (Hono) web SPA, teammates, cron, CI
CLI packages/cli shell operators (sync, backups, migrate)

The REST API also serves the built web SPA from the same Hono process, so the UI and API share one origin (no CORS). The web Chat's server-side agent spawns the MCP server as a subprocess and drives the same tools, so the reasoning path and the local-agent path converge on the same core.

The two loops, plus a third way in

Two loops run around work items:

  • Ingest. Analyze a work item, then save an approved lesson. Nothing becomes knowledge until a human approves it.
  • Consult. Given a new work item, surface relevant past lessons.

And a third path skips the work item entirely: load context. Feed in freeform material (a codebase overview, a runbook, an architecture note) that is not a single ticket. It is stored as reference docs, chunked and embedded, and surfaces in search_reference and get_context alongside the lessons. This is how you seed the archive before any ticket exists.

Curation and org structure support all three.

See Packages for the per-package breakdown.

Clone this wiki locally