Every layer a message passes through, what's really running versus what the docs claim, the last four months of real work, and one bug worth fixing today. Built by tracing the live Hetzner box directly — not summarizing planning notes.
The short version: real users talk to Grok 4.3 through a genuinely working pipeline — routing, memory assembly, mechanical safety gates, delivery. A local Gemma 4 model has been fine-tuned three times with real measured gains but has never served a real user. The engine has been deliberately frozen at a stabilization checkpoint since July 15 — the last month's real work was dataset growth and monitoring infrastructure, not new architecture. And one safety-path regression, live since July 11, needs a fix now — details below, not buried.
Every claim below is cited to a file, line, commit, or a live check performed today. Where the architecture docs and the running code disagree, the code wins — and the disagreements are called out explicitly, not smoothed over.
Not a five-layer memory system running a local model on-device — that's the design doc. The thing real users talk to today is narrower and more concrete.
Production's own system prompt describes it plainly: a Telegram-based family companion for ordinary stress, chronic overload, and crisis-adjacent moments — expected to be specific and useful, not just emotionally warm. api.py:748-752
Fair public description: a memory-enabled personal and family AI companion that combines conversation, parenting/coaching support, household and life-management skills, and persistent context across sessions — running on a cloud frontier model today, with a fine-tuned local model as an active but not-yet-shipped research track.
Click a step to see what actually happens there, cited to the real function and line.
oimy-photon-imessage) is running as of this audit, ahead of its "planned" status in older docs./chat endpoint decides whether this is a continuation or a new session, runs a narrow deterministic medical-emergency check (chest pain/breathing, fever + stiff neck), and checks for a pending bridge response in flight.api.py:2165-2212skill_id and confidence. The manifest entry supplies a workflow_type — chat_light, action, coach, expert, planner, monitor, or profile. Action and monitor types face an extra confidence gate before they're allowed to execute.api.py:2482-2487, 2741-2767_execute() routes to the matching archetype. A direct chat/companion turn goes to Grok 4.3 over OpenRouter; a coach turn can instead hit a DeepSeek V4 Flash scaffold, or escalate to a Claude Sonnet 4.6 "tall model" path — the model that answers depends on routing, not one universal companion.api.py:6042-6073, 4753, 4803-4885session_suggestions, the full coaching anchor file (size-capped), the last eight raw history turns, H30 probing instructions, and — if a crisis pattern matched — a safety-alert system addition.api.py:5461-5599patpat · workflow coach · high confidencedeepseek-v4-flash scaffold — not Grok 4.3Source: docs/synthetic-user-testing/session-logs/haiku5-session-003.jsonl — a synthetic test, not a live user conversation.
The documented architecture has five memory layers. Two are fully built and live for everyone. One is built but switched off by default. Two don't exist yet.
OIMY_MEMORY_TIER actually gatesLayer 3 isn't binary — it's a config flag, and production doesn't set it, so it defaults to the least-rich option.
This is the exact gap the taste-layer proposal below sits on top of — even Tier 2's confidence decay isn't live, so there's no durable signal today for "this specific thing worked for this user," only raw fact recall.
Easy to assume these are one system. They aren't:
| Store | Holds | Owner |
|---|---|---|
SQLite oimy.db | Entity facts, profile, H30 state, recent messages, inference state, outbox | The companion engine itself |
SQLite vector_memory.db | 384-dim embeddings for semantic search | The companion engine itself |
| Postgres 17 | users, instances, user_sessions, user_chat_messages | The surrounding platform / control plane |
The engine process has no Postgres connection at all — the two stores don't talk to each other directly.
| Role | Live model | Notes |
|---|---|---|
| Router | gpt-5.4-mini | One cheap classification call per turn |
| Companion (default) | x-ai/grok-4.3 | What most real replies come from |
| Fallback | claude-haiku-4.5 | If the primary call fails |
| Coaching scaffold | deepseek-v4-flash | Common for coach-routed turns — see the trace above |
| Deep-reasoning / "tall" | claude-sonnet-4.6 | The COACH_MODEL env var is set but not actually read by the code — this is the real control |
| Gemma 4 12B QAT + LoRA | eval / fine-tuning only | Never serves a real user message, in production or dev |
v2 (19,074 examples) was a real +0.83 gain over baseline but under-delivered on multi-part asks. v3.1 added 3,400 reasoning-trace examples, fixed that gap, but landed at roughly a wash overall (6.97) with a new terseness quirk on short exchanges. Neither has shipped — the runbook explicitly says to reset production to Grok after each eval run.
The mechanical safety gates work as designed for most of what they check. One path doesn't, and it's the crisis-escalation path.
Live defect, reproduced against production code today. When a message trips the crisis/escalation veto — correctly redirecting something like an "action" request away from blind execution — the fallback companion call passes request_ctx=request_ctx. That variable is never defined in _execute(). It throws, gets caught by a broad exception handler, and silently falls through to a static generic reply.
Introduced 2026-07-11 (commit 080094a), live since. Reproduced with two real inputs against the checked-out production module:
"What warning signs should I watch for if he is getting depressed?"
→ NameError: name 'request_ctx' is not defined
→ shipped: "I'm here for you! What would you like to talk about?"
Worst case is third-person concern — a parent asking about someone else, not themselves. _detect_parent_crisis()'s patterns are mostly first-person, so third-person concern relies entirely on _detect_escalation_signal(), which hits this exact crash with no safety net behind it. First-person crisis language lands slightly softer — a crisis-specific static fallback can still fire after the failed call — but that's a floor, not a fix.api.py:6042-6128, 4368-4391
Fix scope is small: request_ctx just needs to be removed or properly threaded through the fallback call at api.py:6112-6121.
_roster_unknown_names()_ledger_exclusion_violations()One reliability caveat worth knowing: the embedding-bank import is fail-open — if it errors at startup, the checks silently disable rather than blocking boot. Worth a health-check line, not currently monitored.
The engine's own git history only goes back to July 11 — everything before that lived only on the production server. Here's the real, dated shape of the work, not a manufactured "steady progress" narrative.
The honest read: the core engine has been held still on purpose since July 15, per its own stated reasoning — stabilize before building the next layer ("Heavy Hermes") — while the family-simulation test corpus and operational monitoring kept expanding underneath it.
Tap a claim to see what's actually true today.
TALL_MODEL, plus a DeepSeek scaffold used for most coach turns.if False).| Phase | What | Status |
|---|---|---|
| 0 — Auth hole | Closed unauthenticated JWT endpoint | fixed everywhere |
| 1 — Request isolation | Explicit per-request context, no shared thread-local state | dev + 1-account canary |
| 2 — Durable delivery | Turn ledger + outbox | fully live |
| 3 — Context API | /context + /context/writeback | dev + 1-account canary |
| 4 — Bounded server | Rate-limited, health-checked FastAPI/Uvicorn | dev + 1-account canary |
| 5 — Monitoring/alerting | Automatic failure detection | not started |
| 6 — Data retention/auth hardening | — | not started |
| 7 — Real testing program | Formal external testing | not started |
The "1-account canary" in Phases 1, 3, and 4 is the founder's own Telegram account — confirmed live in the running config, unchanged from July 15.
Light Hermes (live) is router-only — no persona, no memory. Heavy Hermes (designed, not built) would give the gateway a full adaptive persona fed via a direct code hook instead of a stuffed prompt. Deferred deliberately: an independent review found only 1 of 6 real recent production bugs was actually an architecture gap, so the core engine gets stabilized first. The forcing reason it exists at all: the vendor Hermes gateway caps personas at 20,000 characters, and OiMy's real coaching/knowledge file is roughly 6x that.
Built to route complex multi-person "deliverable" turns to a bigger model. Tested net-negative: both return paths skip writing the result back into conversation memory, causing wrong-fact errors next turn (trust score ~9.85/10 bridge-off vs. ~3.5/10 bridge-on in eval). DISABLE_BRIDGE has never been explicitly set in production — flagged in July as needing a decision, still unset today.
Prompted by an outside read on agent memory design — the gap it names lines up exactly with what §03 shows: OiMy has durable fact recall and ephemeral anti-repetition tracking, and nothing in between that remembers why something worked for a specific person.
The gap. h30_profile has two kinds of state: durable classification (quadrant, BCT level, re-inferred every 10 messages) and ephemeral anti-repetition tracking (session_suggestions, capped at 8, wiped after a 4-hour idle gap). BCT_HINTS are static per-bucket — same hint for every "individualist," never refined by what actually landed for this one person.
Proposed h30_taste_signals table — gated on explicit signal only ("yes exactly," "keep doing that," or pushback like "I don't need generic advice"), each capture storing what landed/didn't, which axis it maps to (tone, structure, length, clinical-language sensitivity), and a confidence score — capped at ~20-30 per user, same deliberately-small spirit as the suggestion cap. Consumed alongside BCT_HINTS as observed-for-this-user rather than assumed-for-this-bucket. Review cadence piggybacks on the existing 10-message reinference cycle instead of a new job.
Plausibly adjacent to the unsolicited_advice / emotional_bypass flags already being chased — the addendum-exception fix and clinical filter patch symptoms at the prompt layer, but nothing remembers "this user specifically hates being redirected to logistics mid-vent" after it happens once.
How this was built. Two independent verification passes against the live Hetzner box on 2026-08-16, cross-checked against each other and against the published July 15 architecture brief. Disagreements were resolved in favor of whichever claim was backed by an execution test or a live process/config read, not a comment or a doc.
Full findings and citations available on request. Sensitive material (credentials, exact security-fix specifics) intentionally excluded from this page.