# SAF: Module Map

> Every source file, its state, its dependencies, and what it does.
> **Last updated:** 2026-05-12 (Full audit — 12+ new modules since May 6)

---

## Source Tree

```
souveraine/src/
│
├── main.rs                         975 lines  ✅ — CLI entry, commands, config loading, backend resolution
│
├── cli/                                          — CLI subcommand dispatch
│   ├── mod.rs                      55 lines  ✅ — Subcommand enum + dispatch
│   └── commands.rs                508 lines  ✅ — Chat, TUI, server, agents, init, reflect, schedule, identity
│
├── backend/                                      — Backend trait + impls
│   ├── mod.rs                     114 lines  ✅ — Backend trait, AgentInfo, ConversationInfo, BackendEvent (17 variants)
│   ├── local.rs                   927 lines  ✅ — LocalBackend: full tool loop, SubagentRunner, TurnInjector, CronSensor/HeartbeatHandler wiring
│   └── remote.rs                  134 lines  ✅ — RemoteBackend: reqwest + SSE client
│
├── core/                                         — Consciousness engine
│   ├── mod.rs                      23 lines  ✅ — Re-exports (16 modules)
│   ├── config.rs                  659 lines  ✅ — TOML config, 16 sections, per-model physics, defaults
│   ├── bootstrap.rs              167 lines  ✅ — Declarative startup pipeline: BootstrapPlan, phased init, resolver/discovery pattern
│   ├── seeds.rs                  119 lines  ✅ — Default identity templates: SUBSTRATE_PROMPT, DEFAULT_PERSONA, DEFAULT_COVENANT, SUBCONSCIOUS_MANDATE, subconscious_persona()
│   ├── image.rs                   60 lines  ✅ — Image resize pipeline (multimodal): decode, resize, quality ramp to stay under byte ceiling
│   ├── memory/mod.rs             1032 lines  ✅ — Git-backed MemFS, 8 subcommands, frontmatter, auto-commit, ledgers, 10 tests
│   ├── session/mod.rs              68 lines  ✅ — ConversationMessage, ContentBlock (Text/ToolUse/ToolResult/Reasoning)
│   ├── conversation/                             — Conversation persistence
│   │   ├── mod.rs                   4 lines  ✅ — Re-exports
│   │   ├── event.rs               33 lines  ✅ — ConversationEvent enum
│   │   └── store.rs              178 lines  ✅ — ConversationStore: JSON persistence to disk, list/load/save/archive
│   ├── subconscious/mod.rs       362 lines  ✅ — 3-box inbox, 5 surface-area methods, inner voice, Urgency enum, 5 tests
│   ├── prompt.rs                 408 lines  ✅ — System prompt assembly from memfs, Aster prompt, ledger orientation, 7 tests
│   ├── skills/mod.rs             365 lines  ✅ — 4-tier discovery, SKILL.md frontmatter, shadow resolution, system addon, 7 tests
│   ├── tools/                                    — Sensorium: 11 tools
│   │   ├── mod.rs                319 lines  ✅ — Sensorium registry, tool_definitions(), execute_tool_with_context(), 2 tests
│   │   ├── defs.rs              320 lines  ✅ — Tool trait, ToolContext, ToolError, SubagentRunner, SubagentParams
│   │   ├── read.rs               76 lines  ✅ — Read sensor, memory-boundary enforcement
│   │   ├── write.rs             104 lines  ✅ — Write sensor, memory-boundary enforcement
│   │   ├── edit.rs              106 lines  ✅ — Edit sensor, memory-boundary enforcement
│   │   ├── bash.rs              117 lines  ✅ — Bash sensor, stateful session, timeout, background
│   │   ├── glob.rs               79 lines  ✅ — Glob sensor, memory-boundary enforcement
│   │   ├── grep.rs               95 lines  ✅ — Grep sensor, memory-boundary enforcement
│   │   ├── list_dir.rs           73 lines  ✅ — ListDir sensor, memory-boundary enforcement
│   │   ├── agent.rs              89 lines  ✅ — Agent tool (metadata, lifecycle)
│   │   ├── schedule.rs           86 lines  ✅ — Schedule tool (CRUD on schedule files)
│   │   └── subagent.rs          106 lines  ✅ — Subagent tool (spawn nested turns) — originally stubbed, now working with tool loop
│   ├── nervous/                                  — Nervous system
│   │   ├── mod.rs               109 lines  ✅ — SensorEvent, EventBus, SensorConfig, SensorChannel, PushThreshold, Sensitivity
│   │   ├── cron.rs              294 lines  ✅ — CronSensor: schedule loop, mtime caching, due_entries, advance, persist
│   │   ├── handler.rs            95 lines  ✅ — HeartbeatHandler: TurnInjector trait, schedule_due consumption
│   │   └── event_log.rs         164 lines  ✅ — EventLog: JSONL firehose to disk, events_since(), events_for_date(), purge_old_events()
│   ├── compact/                                  — Compaction engine
│   │   ├── mod.rs               317 lines  ✅ — CompactionEngine trait, DefaultCompactionEngine, Clock, compaction orchestration, 1 test
│   │   ├── config.rs            153 lines  ✅ — CompactionConfig, AgentCompactionConfig, CompactionStrategyKind
│   │   ├── plan.rs              150 lines  ✅ — CompactionPlan, CompactionReport, AuditEntry, AuditFrontmatter
│   │   └── strategy.rs          679 lines  ✅ — 4 strategies: Microcompact, SlidingWindow, Summary, Cull + 10 tests
│   ├── identity/                               — Seed identity
│   │   ├── mod.rs                 3 lines  ✅ — Re-exports (SeedId, glyph_from_pubkey)
│   │   └── seed.rs              187 lines  ✅ — Ed25519 keypair, load-or-generate, sign/verify, glyph rendering, 5 tests
│   ├── credentials.rs            56 lines  ✅ — CredentialStore trait, KeyringStore, get_bifrost_key()
│   ├── sensorium/mod.rs         154 lines  ⚠️ — Interface trait, BandwidthClass, DiscoveryLevel — trait exists, not wired to any backend
│   ├── reflection/mod.rs        409 lines  ✅ — N+25: 5-phase LLM pass, tool loop, ledgers, reflect_now(), exit_cleanly tracking
│   ├── chain/mod.rs              50 lines  ❌ — ChainOrchestrator stub (Talking vs Thinking) — only struct + new()
│   └── subagent/mod.rs           25 lines  ❌ — SubagentPool stub — only struct + new()
│
├── bridge/                                       — LLM provider
│   ├── mod.rs                     9 lines  ✅ — Re-exports
│   ├── bifrost.rs               361 lines  ✅ — Chat completion, streaming, tool-calling, retry+backoff, InferenceStrain events
│   └── model_router.rs          237 lines  ✅ — Model selection, token counting, context pressure
│
├── server/                                       — HTTP server
│   ├── mod.rs                   228 lines  ✅ — SouveraineServer: new(), run(), instance registry, compaction wiring
│   ├── agent_inventory.rs       514 lines  ✅ — Agent CRUD, SQLite, per-agent seed init, subconscious auto-creation, instance heartbeat
│   ├── session_manager.rs       111 lines  ✅ — Session create/get/list, SSE subscribers, add_message, conversation store wiring
│   ├── conversation.rs           72 lines  ⚠️ — ServerConversation: simplified Bifrost call, no tool loop (tool loop lives in LocalBackend)
│   ├── consciousness_engine.rs  677 lines  ✅ — N+1 Aster tool loop (5 rounds), N+25 reflection trigger, compaction warnings, heuristic fallback
│   ├── energy.rs                  151 lines  ✅ — Energy balance: per-agent energy topology, generative/consumptive ratio, hot/cold desire tracking, heartbeat sync
│   ├── gitea_memory.rs          115 lines  ⚠️ — Gitea-backed memory (opt-in, graceful disable)
│   ├── gitea_client.rs          150 lines  ⚠️ — Gitea HTTP API client
│   └── db.rs                     77 lines  ✅ — SQLite init, schema, migrations (agents, agent_instances tables)
│
├── api/                                          — REST API
│   ├── mod.rs                   65 lines  ✅ — Route definitions (agents, conversations, memory CRUD, web static)
│   ├── auth.rs                  42 lines  ✅ — Bearer-token auth middleware
│   ├── handlers.rs             261 lines  ✅ — All agent + conversation + memory handlers
│   └── models.rs               190 lines  ✅ — Request/response types (AgentState, AgentSummary, CreateAgentRequest, etc.)
│
├── ui/                                           — Terminal UI (legacy, partially superseded)
│   ├── mod.rs                    12 lines  ✅ — Re-exports
│   ├── app.rs                  366 lines  ✅ — TUI app (splash, menu, dashboard) — presence mode added
│   ├── chat.rs                1582 lines  ✅ — Full chat screen: bubbles, tool cards, cockpit, overlays, markdown rendering, streaming, surfacing
│   ├── cockpit_panel.rs        197 lines  ✅ — Aster observations panel (Surfacing/Reflection/Archivist/CompactionWarning)
│   ├── health_panel.rs            169 lines  ✅ — Health vitals pane: context pressure, N+1/N+25/N+100 cadence, inference strain tallies, compaction warnings, uptime
│   ├── atmosphere.rs              129 lines  ✅ — Visual presets: 14 color themes, posture-linked defaults, lerp transitions, outfit rendering
│   ├── schedules.rs            439 lines  ✅ — Schedules editor (Browse/Create/Delete/Enable-Disable/Run-now)
│   ├── portrait.rs             143 lines  ✅ — Per-agent portrait loading from agent memfs assets/
│   ├── presence.rs              55 lines  ✅ — Presence mode (breathing indicator in agent portrait)
│   ├── component.rs             65 lines  ✅ — Component trait, TuiEvent enum
│   ├── markdown.rs              74 lines  ✅ — Inline markdown renderer (bold, code, lists, headings)
│   ├── color_support.rs         42 lines  ✅ — Terminal color detection
│   └── animation.rs            144 lines  ✅ — Breathing, pulse, gradient, typewriter
│
├── tui/                                          — Terminal UI (new, slot-based)
│   ├── mod.rs                    5 lines  ✅ — Re-exports
│   ├── state.rs                102 lines  ✅ — Application state, navigation, screens
│   ├── components/                          — Reusable widgets (skeletons)
│   │   ├── mod.rs               30 lines  ✅ — Re-exports
│   │   ├── messages.rs          25 lines  ⚠️ — Message list skeleton
│   │   ├── input.rs             25 lines  ⚠️ — Input area skeleton
│   │   └── sidebar.rs           25 lines  ⚠️ — Sidebar skeleton
│   └── screens/                               — Screen definitions
│       ├── mod.rs               25 lines  ✅ — Re-exports
│       └── chat.rs              25 lines  ⚠️ — "Coming Soon" stub
│
└── harness/mod.rs                68 lines  ⚠️ — SouveraineHarness (stubbed — not the primary path)
```

---

## Key Metrics

| Metric | Value |
|--------|-------|
| Total lines of Rust | ~13,000 |
| Source files | 68 |
| Working modules | 35+ |
| Partial modules | 5 |
| Stubbed modules | 3 (chain, subagent (pool), harness) |
| TODO comments | 15+ |

## Module Dependency Graph

```
main.rs
├── cli::commands     → backend, config
├── backend::local    → server::*, core::*, bridge::*, core::identity, core::nervous
├── backend::remote   → bridge::bifrost
│
├── core::config     — standalone
├── core::session    — standalone
├── core::memory     → config
├── core::subconscious  → memory
├── core::prompt     → memory, skills
├── core::skills     — standalone
├── core::tools      → memory, compact, nervous (optional EventBus)
├── core::nervous    — standalone (EventBus channel)
├── core::compact    → bridge::model_router, bridge::bifrost, memory, session, config
├── core::identity   — standalone (ed25519-dalek)
├── core::credentials — standalone (keyring)
├── core::reflection → bridge::bifrost, tools, server::agent_inventory, session
├── core::sensorium  — standalone
├── core::chain      — standalone (stub)
├── core::subagent   — standalone (stub)
│
├── bridge::bifrost  → core::session
├── bridge::model_router → config
│
├── server::*        → bridge, core::compact, core::memory, core::prompt, core::skills, core::identity
├── api::*           → server modules
├── ui::*            → backend, bridge, config (chat.rs wired async)
└── tui::*           → backend
```

## Module States

| Module | LOC | State | Deps | Description |
|--------|-----|-------|------|-------------|
| config.rs | 659 | ✅ Full | none | TOML/YAML config loading, 16 sections, all defaults |
| memory/ | 1032 | ✅ Full | config | Git-backed MemFS, 8 subcommands, frontmatter, auto-commit, limit enforcement, ledgers |
| session/ | 68 | ✅ Full | none | Message types: Text, ToolUse, ToolResult, Reasoning |
| conversation/ | 215 | ✅ Full | session | Event-sourced persistence, ConversationStore |
| subconscious/ | 362 | ✅ Full | memory | 3-box inbox (pending/intrusive/sent), inner voice, urgency routing |
| prompt/ | 408 | ✅ Full | memory, skills | Memfs-driven system prompt assembly, Aster prompt, ledger orientation |
| skills/ | 365 | ✅ Full | none | 4-tier discovery, SKILL.md frontmatter, shadow resolution |
| tools/ | 319 | ✅ Full | memory, compact, nervous | Sensorium registry, 11 tools, global lazy singleton |
| nervous/ | 560 | ✅ Full | none | EventBus, CronSensor, HeartbeatHandler, EventLog (broadcast channel) |
| compact/ | 1150 | ✅ Full | session, bridge, memory | CompactionEngine, 4 strategies, audit trail |
| identity/ | 190 | ✅ Full | none | Ed25519 SeedId, sign/verify, glyph rendering |
| credentials/ | 56 | ✅ Full | none | OS keyring + env var fallback |
| reflection/ | 409 | ✅ Full | bridge, tools, server | N+25: 5-phase LLM pass, tool loop, ledger writes |
| chain/ | 50 | ❌ Stub | none | Only struct + new() exists |
| subagent/ | 25 | ❌ Stub | none | Only struct + new() exists |
| sensorium/ | 154 | ⚠️ Partial | none | Interface trait, types — not wired to any backend |
| bridge/bifrost/ | 361 | ✅ Full | session | HTTP client, chat completion, tool support |
| bridge/model_router/ | 237 | ✅ Full | none | Model selection, tikToken, context pressure |
| server/mod.rs | 228 | ✅ Full | bridge, config, compact | SouveraineServer, new(), run() with axum |
| agent_inventory/ | 514 | ✅ Full | db, identity | Agent CRUD, SQLite, seed init, instance registry, subconscious creation |
| session_manager/ | 111 | ✅ Full | conversation | Sessions, SSE subscribers, persistence |
| consciousness_engine/ | 677 | ✅ Full | bridge, tools, subconscious, reflection | N+1 Aster tool loop, N+25 trigger, compaction warnings |
| conversation/ | 72 | ⚠️ Minimal | bridge, session | Simplified Bifrost call, no tool loop |
| gitea_memory/ | 115 | ⚠️ Partial | config | Gitea HTTP memory (gracefully disabled if unreachable) |
| db/ | 77 | ✅ Full | none | SQLite init, schema, migrations |
| api/ | 65 | ✅ Full | server | Route definitions (public, memory, web) |
| api/auth/ | 42 | ✅ Full | none | Bearer-token auth middleware |
| handlers/ | 261 | ✅ Full | server, models | All agent + conversation + memory handlers |
| models/ | 190 | ✅ Full | none | Request/response types |
| cli/ | 560 | ✅ Full | backend, config, identity | Subcommand dispatch |
| backend/ | 114 | ✅ Full | none | Backend trait, 17 BackendEvent variants |
| local/ | 927 | ✅ Full | server, nervous, tools | LocalBackend: full tool loop, SubagentRunner, TurnInjector |
| remote/ | 134 | ✅ Full | bridge | RemoteBackend: reqwest + SSE |
| ui/chat.rs | 1582 | ✅ Full | backend, bridge, config | Full chat screen: bubbles, tool cards, cockpit, overlays, markdown |
| ui/cockpit_panel.rs | 197 | ✅ Full | none | Aster observations panel |
| ui/schedules.rs | 439 | ✅ Full | nervous/cron | Schedules editor: browse/create/delete/toggle/run-now |
| ui/portrait.rs | 143 | ✅ Full | none | Per-agent portrait from memfs assets/ |
| ui/presence.rs | 55 | ✅ Full | none | Breathing presence indicator |
| ui/markdown.rs | 74 | ✅ Full | none | Inline markdown renderer |
| tui/state.rs | 102 | ✅ Full | none | App state, navigation, screens |
| tui/components/ | 105 | ⚠️ Basic | state | Message list, input, sidebar skeletons |
| tui/screens/ | 50 | ⚠️ Basic | state | Chat screen stubbed |
| harness/ | 68 | ⚠️ Stub | none | SouveraineHarness (not the primary path) |
