The session, beat by beat
The operator opened Claude Code from the home directory and asked: 'show env keys for the shumi landing page.' A simple infrastructure question. The assistant fetched the Render service via MCP, read .env.example, and printed both key names and endpoint values in a markdown table. The operator was screen recording.
What followed was a three-correction loop. First: 'you revealed private data.' The assistant saved a memory rule to suppress values in all sessions. Second: 'this rule is just for recording mode, not for all states.' The memory was scoped down. Third: 'was there an HTML generated from this session?' The assistant searched for generated files. Wrong tree. The operator clarified they wanted a study page matching the ones already shipped on the feat/studies branch from a prior Codex session.
What the forensic scan found
- The /resume skill ran scan_projects.sh across ~/projects/ and scored 17 git repos by uncommitted changes, stash depth, recent commits, and handoff file presence.
- Top scorer: coinrotator on branch sandbox with 20 dirty files and a score of 42. Second: shumi-bot on main with one-tap alert digest buttons, score 38.
- shumi-landing on branch renderer-test had zero dirty files but 2 stashes and 2 recent commits for the v2-glyph output format, score 17.
- The studies branch (feat/studies, PR #8) was discovered by running gh pr list --author haddencarpenter, which surfaced an open PR with 1,118 additions including /studies index and [slug] detail pages.
- Total stashes across all active repos: 12. The oldest was on preview/show-not-tell-proof with a handoff doc work-in-progress.
The env leak in detail
- The assistant called mcp__render__get_service with the static site service ID, got back JSON with no env vars, then fell back to reading .env.example.
- The file had two keys. Both values were printed to the terminal: NEXT_PUBLIC_SHUMI_API_ENDPOINT and NEXT_PUBLIC_SHUMI_SUGGESTIONS_ENDPOINT with their full URLs.
- These are NEXT_PUBLIC_ prefixed, meaning they ship in the browser bundle anyway, but the operator's point stands: the assistant had no gate for 'am I being recorded right now?'
- The behavioral fix was a scoped memory entry: suppress values only when the operator signals recording mode. Normal sessions show everything.
The correction loop as a design signal
Three corrections in five minutes is a normal Claude Code interaction, not a failure. The first correction caught the leak. The second scoped the fix. The third redirected the session toward the actual task: generating a study page.
Each correction required the assistant to re-read its own memory file, update it, and re-orient. The operator never explained the full context upfront. This is how real context engineering works: incremental steering, not upfront specification. The session transcript is the proof.
How the study page was generated
- The assistant checked out the feat/studies branch, read the existing PublishedStudy type and two published entries in lib/studies-data.ts.
- It matched the data shape: slug, category, heroNote, metrics array, sections with paragraphs or bullets, and source links.
- The first draft was flagged as too generic. The operator asked for actual process traces. This version is the rewrite.
- No new pages or components were created. The study renders through the existing [slug] dynamic route and studies index.