Day 24 — 'the rebuild is when transitive resolution stops lying.'
Set out to make 50 lifestyle skills for Werbos. Ended with 80 across eight themed batches (food, health, money, home/travel, mystical, therapy, finance, marketing) — PROMPT_SKILLS 45 → 125, +4,531 lines, two new categories. The deploy taught the lesson the source code wouldn't: the slim runtime image had been borrowing httpx transitively from a sibling, and one sibling refresh later, that loan was called in. Prod crashed on rebuild, then came back with the missing dep declared. dispatch_skill auto-picks up every new skill; traces flow joined by trace_id across slash → llm.
“the rebuild is when transitive resolution stops lying.”
Set out to make 50 lifestyle skills. Ended with 80 across eight
themed batches, two new categories, +4,531 lines of PROMPT_SKILLS
entries. The deploy taught the lesson the source code wouldn’t.
The lifestyle skill bundle
PROMPT_SKILLS 45 → 125. Eight batches of 10, all auto-flowing
into custom_skills reserved-name protection, the dispatch_skill
tool router, and the Skills-tab catalog. Two new categories registered:
finance, marketing. (1c8ec0a)
- Food & Drink:
/grocery·/cocktail·/leftovers·/dietary-swap·/wine-pair·/snack·/potluck·/lunchbox·/coffee-pick·/spice-sub - Health & Body:
/hydrate·/sleep-tip·/workout·/stretch·/posture·/symptom·/eye-rest·/cold-shower·/step-goal·/body-scan - Money & Logistics:
/tip-calc·/price-check·/subscription-audit·/coupon-ideas·/negotiate·/countdown·/timezone·/age-calc·/weekday·/recycle-check - Home, Errands & Travel:
/errands·/fix-it·/plant-care·/laundry·/pest-id·/packing·/layover·/jetlag·/phrase·/small-talk - Mystical & Reflection:
/runes·/iching·/astrology·/numerology·/oracle·/palm·/dream·/moon-phase·/intention·/mantra - Therapy & Inner Work:
/cbt-reframe·/trigger-trace·/self-compassion·/anxiety-spiral·/anger-cool·/boundary-script·/people-please-check·/burnout-check·/therapist-prep·/inner-child - Personal Finance:
/budget-build·/emergency-fund·/debt-payoff·/paycheck-allocate·/401k-check·/roth-vs-traditional·/invest-101·/rent-vs-buy·/insurance-audit·/lifestyle-creep - Marketing & Copy:
/headline·/tagline·/value-prop·/positioning·/landing-copy·/cold-email·/email-subject·/social-post·/seo-meta·/brand-voice
Safety patterns baked in
- Every therapy skill carries a crisis-override block (988,
1-800-799-7233, ER) for suicidal ideation, abuse, trauma
flashbacks, severe persistent symptoms. Modeled on
symptom’s escalation pattern. - Every finance skill refuses to fabricate current tax brackets, contribution limits, or interest rates — those drift yearly. References “the current 402(g) limit” instead of a number, and routes individualized advice to a fee-only CFP or CPA.
- Math-heavy skills (
tip-calc,countdown,timezone,age-calc,weekday) show the work so the LLM’s arithmetic is auditable. For high-stakes uses, a short cross-check nudge. - Marketing skills mark placeholders explicitly
(
<TESTIMONIAL FROM REAL CUSTOMER>) rather than fabricating quotes / logos / stats. No dark-pattern recipes.
The deploy taught the lesson
The skills committed and pushed clean. The SR8 deploy did not.
redeploy.shfailed on the nginx chat-builder Docker stage.npm run buildcouldn’t findtsc. Unrelated to the prompts.py change; pre-existing breakage in the chat-UI build chain. The full compose-up was gated on chat-builder, so the whole stack stayed on the old build.- Backend-only fallback —
docker compose up -d --build werbosto skip the broken chat-builder. The new werbos container built successfully, then crash-looped on startup:ModuleNotFoundError: No module named 'httpx'. Production was down. - Root cause —
werbos/tools/{ollama_chat, fetch_crypto, fetch_weather, fetch_stocks, fetch_definition, fetch_news}all importhttpx, butpyproject.tomlnever declared it. The local dev env hadhttpxtransitively via a sibling; the slim runtime image had it via the same sibling — until that sibling dropped it in a recent commit. The Dockerfile’s hand-listed runtime deps (websockets,starlette,uvicorn) didn’t fill the gap because the next step doespip install --no-depson the wheel. - Recovery — declared
httpx>=0.27,<1inpyproject.toml(c5922d6) AND inorchestration-deploy/Dockerfile.werbos(7efd6b5, orchestration-deploy repo). SSH pull both repos, rebuild. Container uphealthyin 10 seconds.
The moral: transitive resolution is the kind of thing that lies to you in dev and tells the truth on rebuild.
What was already there that this proved
dispatch_skillauto-derives fromPROMPT_SKILLS. All 80 new skills are visible to the chat LLM as natural-language dispatches with no extra wiring. “give me a tarot reading on my new job” →dispatch_skill(name='tarot', args='new job'). ~3–4K of system-prompt overhead at 125+ skills, acceptable on the local 8B.- Traces are flowing. A test
/jokecall produced two correlated trace events in/data/traces/2026-05-28.jsonlwith the sametrace_idjoining theslashdispatch to thellmcompletion. UUIDv7, daily file, 0600 perms — as designed by the Day 23 tracing commit. custom_skillsreserved-names protection auto-picks up the new surface. No risk of a future user-uploaded custom skill shadowing/dietary-swapbecause_compute_reserved_names()readsPROMPT_SKILLSdirectly.
Numbers worth keeping
- PROMPT_SKILLS: 45 → 125 (+80, +178%)
- Categories: 10 → 12 (added
finance,marketing) - Lines added to
werbos/prompts.py: +4,531 - Test suite after the change: 4,553 pass, 2 pre-existing
failures unrelated to this work (
dispatch_skillregistry inheritance) - Deploy attempts: 3 (one full-stack fail, one backend-only crash, one recovered)
- Minutes of prod downtime: ~10
- Lines in the Dockerfile fix: +2
Aphorisms
“transitive resolution lies to you in dev and tells the truth on rebuild.”
“the catalog auto-grows; the per-skill cost approaches zero, but the system-prompt token cost does not.”
“OH these are for Werbos… not Claude…” — the mid-sketch realization that this was a Werbos product expansion, not a Claude Code skill set. ~30 minutes of detour avoided.
Carryover into Day 25
- Fix the nginx chat-builder Docker stage.
tsc not foundblocks any fullredeploy.shrun. Either a missingnpm ci/ devDependencies install step, or a stale Docker layer. Cheap to investigate. - Watch
dispatch_skilltoken cost on the 8B local model. If chat responses lag noticeably, the catalog summary in the tool description is the lever to tighten. - Safety patterns deserve regression tests.
symptom’s escalation block and the therapy crisis-overrides should be in the next security/safety sweep so a future skill edit can’t silently drop them.