diff options
Diffstat (limited to 'inbox')
25 files changed, 18 insertions, 846 deletions
diff --git a/inbox/PROCESSED-2026-06-11-1703-from-home-consolidation-handoff-rulesets.org b/inbox/PROCESSED-2026-06-11-1703-from-home-consolidation-handoff-rulesets.org deleted file mode 100644 index f0a86b7..0000000 --- a/inbox/PROCESSED-2026-06-11-1703-from-home-consolidation-handoff-rulesets.org +++ /dev/null @@ -1,46 +0,0 @@ -#+TITLE: Home is consolidating all personal ~/projects AI projects into itself — heads-up + okay requested -#+DATE: 2026-06-11 - -* What's happening - -Craig approved and started a migration that folds every AI-managed project under ~/projects (except work) into the home project as area subdirectories, with full git history preserved via git filter-repo + merge. End state: ~/projects holds home and work only; ~/code stays the place for standalone code projects. One todo.org, one priority scheme, one .ai session for all personal project management. - -The spec rode along in this same inbox drop (from-home file with "project-consolidation-spec" in the name). It went through a full spec-review cycle (Codex, two passes: Not ready → Ready) and carries the per-fold manifest contract, a two-mode restore runbook, and a layered rollback story (snapper snapshot, untouched server bares, pre-fold tags, retired dirs, 30-day cooling-off). - -* How far we've gone (as of 2026-06-11 ~17:00 CDT) - -- Phase 0 done: git-filter-repo verified, snapper snapshot 5621, memory-dir tar in ~/backups/, pre-consolidation tag pushed. -- Phase 1 done: philosophy folded (pilot). Mode-B rollback drill passed in a disposable clone — the fold is provably removable using only its manifest. -- Phase 2 done: clipper folded (dress rehearsal). First todo.org import with :MIGRATED_FROM: markers and a fold-time triage; first live-link fix (a dirvish bookmark in ~/.emacs.d). -- Both sources retired to ~/projects/.retired/ (not deleted). Server bares untouched. -- Manifests at home:docs/consolidation-manifest-{philosophy,clipper}.org; live inventory gate at docs/consolidation-manifest-inventory.org. - -* Learnings and adjustments so far - -- A manifest can't embed its own redistribution commit's sha (amend changes it). The manifest row now reads "the commit introducing this manifest"; only the merge sha is recorded literally. -- git clone --no-local is the right clone shape for filter-repo's fresh-clone safety check; --force is banned from the runbook. -- The fold-merge branch is read from the source (fb-photo-scraper sits on master, not main — assume nothing). -- Staged freeze instead of full shutdown: the live inventory gate is regenerated per project immediately before its fold, so Craig can keep using not-yet-folded projects until their turn. -- Imported [#D] tasks fall outside the task-review staleness pool (it tracks A-C only) — by design, but worth knowing when verifying an import. -- Source todo.org "Reference" sections (non-task content) merge into the area's notes.org, not into home's todo.org. - -* What we'd like rulesets to think about - -- Edge cases we may not have seen: anything in the templates, workflows, or scripts that assumes one .ai per project under ~/projects (cross-agent-comms discovery, inbox-send target resolution, the ai launcher's project scan, broadcast). -- Future-project plans: whether new personal "projects" should now start as areas inside home rather than standalone ~/projects entries, and whether the templates should say so. -- Any rulesets docs or workflows that name the folding projects as handoff/broadcast targets (finances, jr-estate, etc.) — they'll need updating in our Phase 7 ecosystem pass; a list from your side would help us not miss any. -- The knowledge-base work-root denylist (~/projects/work) is unaffected. - -* Ask: confirmed okay to continue - -Reply to home's inbox with a confirmed okay (or concerns) for folding the remaining projects. The remaining list, in planned order: - -1. jr-estate (Phase 3 — 704M history, 18-task triage, first memory merge) -2. danneel (Phase 4 — 613M history, 10-task triage) -3. finances (Phase 5 — 251M history, 43-task triage) -4. documents, elibrary, health, kit (Phase 6 folds, together) -5. website + little-elisper — relocate to ~/code as standalone AI projects (Phase 6) -6. fb-photo-scraper — delete (unmodified upstream clone; origin recorded in spec D2) -7. Phase 7 ecosystem pass: link sweep, velox migration, rulesets-reference updates, KB node, cooling clock. - -We hold the remaining folds until your reply lands. diff --git a/inbox/PROCESSED-2026-06-11-1703-from-home-project-consolidation-spec.org b/inbox/PROCESSED-2026-06-11-1703-from-home-project-consolidation-spec.org deleted file mode 100644 index b557012..0000000 --- a/inbox/PROCESSED-2026-06-11-1703-from-home-project-consolidation-spec.org +++ /dev/null @@ -1,350 +0,0 @@ -#+TITLE: Project Consolidation — Fold ~/projects AI Projects into Home — Spec -#+AUTHOR: Craig Jennings -#+DATE: 2026-06-11 - -* Metadata -| Status | Ready — Codex spec-review confirmed 2026-06-11 | -| Owner | Craig Jennings | -| Reviewer | Codex (spec-review, 2026-06-11) | -| Related | [[file:../todo.org::*Project consolidation into home][todo.org task]] | - -* Summary - -Fold every AI-managed project under =~/projects/= (except =work=) into the =home= project as area subdirectories, with full git history preserved, so all personal tasks live in one =todo.org= and can be prioritized against each other. The end state: =~/projects/= holds =home= and =work=; =~/code/= holds standalone code projects. Every step is reversible — originals are snapshotted, server bare repos stay untouched until a cooling-off period ends, and a written restore procedure covers both single-project and full rollback. - -* Problem / Context - -Craig manages 12 AI projects under =~/projects/= beside =home= and =work=. Each has its own =.ai/= session machinery, =todo.org=, inbox, memory dir, and git repo on cjennings.net. That isolation was the design — but the life-management projects (finances, jr-estate, danneel, health, kit, clipper, documents…) are all facets of one life, and their tasks compete for the same hours. Today there is no single surface where a [#A] in jr-estate can be weighed against a [#A] in finances; each project's priorities are graded against siblings only. Sessions fragment the same way: a morning touching finances, danneel, and home means three separate session launches, three inboxes, three memory stores, and cross-project handoff files between them. - -The forces: (1) one prioritization surface requires one task file (or at least one repo); (2) these projects are critical — legal disputes, estate settlement, finances — so the migration must be provably reversible; (3) per-project git histories carry evidentiary and reference value (especially danneel and jr-estate) and must survive queryably; (4) the =.ai/= ecosystem (sessions, memories, inboxes, workflows) has per-project state that must merge without loss; (5) other machines (velox at minimum) hold clones whose remotes must not break silently. - -Survey of the candidates (2026-06-11): - -| Project | What it is | .git | Sessions | Open tasks | Memories | Inbox | -|------------------+---------------------------------------------+-------+----------+------------+----------+-------| -| clipper | 19 Clipper St SF rental property | 23M | 6 | 1 | 0 | 0 | -| danneel | 4319 Danneel construction dispute (legal) | 613M | 45 | 10 | 0 | 0 | -| documents | Disaster-prep document vault | 61M | 7 | 8 | 0 | 2 | -| elibrary | Ebook + music library management | 2.4M | 6 | 0 | 2 | 3 | -| fb-photo-scraper | Third-party FB gallery scraper (clone) | 3.4M | 0 | 0 | 0 | 0 | -| finances | Personal finance (Craig + Christine) | 251M | 24 | 43 | 1 | 4 | -| health | Personal health management | 5.9M | 27 | 8 | 1 | 3 | -| jr-estate | JR estate settlement (legal, trust, taxes) | 704M | 44 | 18 | 7 | 2 | -| kit | Keep In Touch — relationship management | 17M | 20 | 20 | 3 | 4 | -| little-elisper | The Little LISPer worked in elisp (study) | 4.7M | 2 | 0 | 0 | 0 | -| philosophy | Philosophy study + discussion notes | 30M | 5 | 0 | 0 | 0 | -| website | Personal Hugo site (deployed from homelab) | 8.6M | 10 | 11 | 0 | 3 | - -All have origin on cjennings.net except fb-photo-scraper (GitHub clone). All =.ai/= dirs are tracked (personal-project model). No project has a live =session-context.org=. Several have small dirty trees (elibrary 2, finances 1, health 1, kit 4, little-elisper 1 files) that must be resolved pre-fold. - -* Goals and Non-Goals - -** Goals -- One repo, one =todo.org=, one priority scheme, one =.ai/= session for all personal (non-work) project management. -- Full git history of every folded project preserved and queryable in place (=git log <area>/= works). -- All =.ai/= state merged without loss: session archives, memories, inboxes, someday-maybe, project workflows/scripts. -- A written, tested restore path for any single project and for the whole migration. -- =~/code/= becomes the only home for standalone code projects. - -** Non-Goals -- No restructuring of home's existing content (homelab docs, assets, music reconciliation dirs stay where they are; re-nesting them under an =infra/= area is vNext). -- No change to the =work= project in any way. -- No task content rewriting beyond re-grading priorities to the unified scheme — bodies, links, and histories move as-is. -- No server-side bare-repo deletion during the migration (archival is a separate, later, post-cooling step). -- No renaming of the =home= project. - -** Scope tiers -- v1: fold the nine life-management projects (clipper, danneel, documents, elibrary, finances, health, jr-estate, kit, philosophy); relocate the code-shaped three (website, little-elisper, fb-photo-scraper) per Decision 2; ecosystem updates (emacs agenda, rulesets references, velox). -- Out of scope: work; any =~/code/= project; home's internal restructure. -- vNext: server bare-repo archival after cooling-off; optional =infra/= re-nesting of homelab content; per-area README normalization. - -* Design - -** End-state layout - -Each folded project becomes a top-level area directory in home, preserving its internal structure: - -#+begin_example -~/projects/home/ - clipper/ danneel/ documents/ elibrary/ - finances/ health/ jr-estate/ kit/ philosophy/ - assets/ docs/ homelab-inventory/ inbox/ scripts/ (existing home content, unchanged) - todo.org (unified) - .ai/ (single session machinery) -#+end_example - -This matches the established area pattern (work's =deepsat/assets/=, the working-files convention's =<area>/assets/=). Each area keeps its own =assets/=, =docs/=, internal org files, and a per-area =.gitignore= carrying its old ignore patterns (git honors nested ignores; prefixing patterns into the root ignore is error-prone). - -** Git history — filter-repo then merge - -For each source project, on a throwaway clone (never the original). =--no-local= forces a real transport-style clone instead of hardlinked/shared objects — the conservative shape git-filter-repo's manual recommends, and what makes the clone a genuine fresh-clone safety check. =branch= is the source's actual default branch (fb-photo-scraper is on =master=; assume nothing): - -#+begin_example -branch=$(git -C ~/projects/<name> symbolic-ref --short HEAD) -git clone --no-local ~/projects/<name> /tmp/fold-<name> -cd /tmp/fold-<name> -git filter-repo --to-subdirectory-filter <name> -cd ~/projects/home -git remote add fold-<name> /tmp/fold-<name> -git fetch fold-<name> -git merge --allow-unrelated-histories -m "feat(<name>): fold <name> project into home" "fold-<name>/$branch" -git remote remove fold-<name> -#+end_example - -=git filter-repo --force= is not part of this runbook. If filter-repo refuses to run, the fresh-clone safety check failed — stop, write down why, and fix the clone rather than overriding. - -=filter-repo= rewrites every historical path under =<name>/=, so after the merge =git log <name>/somefile= shows the file's full history with original commit messages, authors, and dates. The original repo and its server bare are never touched — the rewrite happens on the temp clone only. - -The merged home =.git= grows to roughly 1.8G (dominated by danneel 613M + jr-estate 704M + finances 251M). Acceptable for a private single-user server; noted as a clone-time cost. - -** The .ai/ and task merge (per project, after the git merge) - -The git merge lands the project's files under =<name>/=, including its old =.ai/= and =todo.org=. A post-merge commit then redistributes that state: - -1. /Sessions:/ =git mv <name>/.ai/sessions/*= into home's =.ai/sessions/=, inserting the area into the name: =YYYY-MM-DD-HH-MM-<desc>.org= → =YYYY-MM-DD-HH-MM-<name>-<desc>.org=. Dated names make collisions near-impossible; the prefix preserves provenance. -2. /todo.org:/ append the project's open work as a new top-level section =* <Area> Open Work= (matching =* Home Open Work=), and its resolved section likewise. Each imported section heading carries a properties drawer marking provenance — =:MIGRATED_FROM: <name>= and =:MIGRATED_ON: YYYY-MM-DD= — so the import boundary stays visible to future edits and to the restore runbook. Walk the incoming tasks with Craig to re-grade priorities onto the unified scheme (home's A-D impact/urgency ladder, generalized beyond infra) and add an area tag (=:finances:=, =:jrestate:=, =:danneel:=, …). Then delete =<name>/todo.org=. -3. /notes.org:/ the project's Project-Specific Context moves to =<name>/notes.org= (area-local reference, linked from home's =.ai/notes.org=). Active Reminders and Pending Decisions merge into home's =.ai/notes.org= with area attribution. -4. /Inbox:/ process each project's inbox to zero before the fold (preferred), or move unprocessed items into home's =inbox/= renamed =YYYY-MM-DD-from-<name>-<orig>.ext=. -5. /Workflows + scripts:/ copy =<name>/.ai/project-workflows/*= and =project-scripts/*= into home's, after a filename-collision check (13 workflow files exist across sources; any collision is resolved by area-prefixing the incoming file). Then delete the area's old =.ai/= machinery (=protocols.org=, =workflows/=, =scripts/= — all template-synced duplicates). -6. /someday-maybe.org:/ append under an =* <Area>= header in home's. -7. /Memory:/ copy =~/.claude/projects/-home-cjennings-projects-<name>/memory/*.md= into home's memory dir (rename on slug collision), append index lines to =MEMORY.md=, dedupe against existing entries, then archive the source memory dir into the backup tar (it lives outside git). -8. /Links:/ =grep -rn "projects/<name>" ~/projects/home ~/.emacs.d ~/sync/org ~/org/roam= and fix every absolute reference to the new path. Record the before-count, fix, re-run, and classify any remaining hits as historical (session archives, this spec) or live — live hits block the fold's close. Relative links inside the area survive the move untouched because internal structure is preserved. - -** Per-fold manifest - -Every fold produces a tracked manifest at =docs/consolidation-manifest-<name>.org=, written as the fold proceeds and committed with the redistribution commit. The manifest is the restore contract and the verification record — without it, "every step is reversible" is a slogan. It records: - -- /Source state:/ source path, HEAD sha, branch, =git status --porcelain=v1= output at gate time (must be empty), origin URL. -- /Tracked universe:/ the =git ls-files= listing from the source (or a sha256 of it, with the listing in an appendix block). After the merge, every path must exist under =home/<name>/= or appear in the redistribution map below. -- /Untracked, ignored, and inbox inventories:/ each file listed with its explicit disposition — processed, moved (to where), archived, or intentionally dropped. Nothing leaves the source tree without a line here. -- /Redistribution map:/ sessions moved (old → new names), todo.org section markers added (=:MIGRATED_FROM:= headings), notes/someday-maybe merges, workflows/scripts copied (with collision resolutions), memory files copied + =MEMORY.md= lines added, link rewrites made (=path:line=, before → after). -- /Commits:/ the fold merge commit sha and the redistribution commit sha. -- /Retired path:/ where the source dir went. - -Verification per fold checks path lists against this manifest, not file counts — a count can pass while losing files and fail on intentional redistribution. - -** Safety net and restore - -Layered, oldest-to-newest: - -- /Layer 0 — filesystem snapshot./ Before anything: =snapper create --description pre-consolidation= (ratio's root is btrfs with snapper) plus a belt-and-suspenders tar of the memory dirs: =tar czf ~/backups/claude-memory-pre-consolidation-$(date +%F).tgz -C ~/.claude projects=. Content-only restore is sufficient for the memory tar — memory files are plain-text markdown the harness reads by path; no permissions, ACL, or xattr metadata is load-bearing, so plain =tar czf= is the contract. -- /Layer 1 — server bare repos untouched./ Origin repos on cjennings.net remain exactly as they are through v1. They hold every byte of every project's history independent of anything done locally. -- /Layer 2 — pre-fold tags./ Home gets =git tag pre-consolidation= before the first fold and =git tag pre-fold-<name>= before each subsequent one, pushed to origin. -- /Layer 3 — retired dirs./ After a fold is verified, the source dir moves to =~/projects/.retired/<name>= (not deleted). Deleted only after the cooling-off period. -- /Cooling-off:/ 30 days minimum after the final fold, and not before velox is migrated. Only then does vNext server archival (move bares to =~/git/archive/=) become eligible. - -*** Restore one project — two modes - -/Mode A — resurrect standalone (leaves home alone)./ =git clone cjennings@cjennings.net:git/<name>.git ~/projects/<name>=, restore its memory dir from the tar. The folded copy in home stays as a harmless duplicate (or is removed later via Mode B). This is the fast path when the need is "I want the project back," not "the fold was wrong." - -/Mode B — remove the folded state from home./ A fold is two commits plus out-of-git side effects; removal must unwind all of it, using the manifest: - -1. =git revert <redistribution-commit>= then =git revert -m 1 <merge-commit>=, in that order (newest first). This is the supported path while the fold is recent — before later edits touch the shared files. -2. If either revert conflicts (todo.org and =.ai/notes.org= are hot files — expected once home has moved on), abort it and instead excise manually from the manifest's redistribution map: delete the =:MIGRATED_FROM: <name>= todo.org sections, the area-prefixed session files, the copied workflows/scripts, and =git rm -r <name>/= — one removal commit citing the manifest. -3. Out-of-git effects either way: delete the copied memory files and their =MEMORY.md= index lines (named in the manifest); re-fix any link rewrites if the old path is coming back. - -/Restore everything:/ snapper rollback (or restore the snapshot's =~/projects/=), restore the memory tar, =git reset --hard pre-consolidation= on home plus a coordinated forced push — acceptable on a single-user remote, with the tag as the anchor. - -** Multi-machine - -velox (and any other machine with clones) keeps working against the untouched server bares until its own migration step: pull home (which brings all folded content), then retire its local =~/projects/<name>= clones the same way. Nothing breaks in the interim — the old remotes still exist; they're just frozen. The =ai= launcher discovers projects by =.ai/protocols.org= presence, so retired dirs (moved under =.retired/=, outside its scan roots) drop out automatically. =inbox-send= targets shrink the same way; any rulesets doc or workflow that names a folded project as a handoff target gets updated in the final phase. - -* Alternatives Considered - -** Keep separate repos, unify only the agenda (org-agenda-files spanning all todo.orgs) -- Good, because zero migration risk and Craig's emacs agenda can already span files. -- Bad, because it solves only prioritization-viewing, not management: 10 sessions, 10 inboxes, 10 memory stores remain; Claude still can't see or rebalance the whole picture in one session; cross-project handoffs persist. -- Bad, because priority schemes stay divergent per file. -- Neutral, because it could serve as an interim state, but it builds nothing toward the end goal. - -** git subtree add per project -- Good, because one command per fold, no external tooling. -- Bad, because history isn't path-rewritten: =git log <name>/file= doesn't follow into pre-merge history without =--follow= gymnastics, weakening the evidentiary value of danneel/jr-estate histories. -- Neutral, because content-wise the result is identical; only history ergonomics differ. - -** Import working trees only, archive old repos (no history merge) -- Good, because the home repo stays small and the procedure is trivially simple. -- Bad, because in-place history is lost — every "when did this clause change" question requires resurrecting an archived repo. -- Neutral, because Layer-1 bares preserve history regardless; this is about whether history is /at hand/. - -** One new "life" super-repo instead of growing home -- Good, because a clean slate avoids home's existing 109M history and infra identity. -- Bad, because home is already the hub (biggest session history, the template patterns, Craig's habits) and would itself need folding in — strictly more work for a cosmetic gain. - -* Decisions - -** D1 — Merge strategy: filter-repo + merge per project -- State: accepted -- Context: critical legal/financial histories must stay queryable in place; restore must be possible regardless. -- Decision: We will fold each project with =git filter-repo --to-subdirectory-filter= on a temp clone, merged with =--allow-unrelated-histories=. -- Consequences: easier — full per-area history in one repo, originals untouched; harder — home =.git= grows to ~1.8G, and =git-filter-repo= becomes a migration dependency (AUR: =git-filter-repo=). - -** D2 — Disposition of the code-shaped three -- State: accepted (Craig, 2026-06-11) -- Context: website (Hugo codebase), little-elisper (code study), fb-photo-scraper (third-party clone, no .ai) are code-shaped, and the target model says code lives standalone in =~/code/=. -- Decision: We will move website and little-elisper to =~/code/= as standalone AI projects (plain =mv= + memory-dir rename, same as the homelab→home rename runbook), and delete fb-photo-scraper (it's an unmodified upstream clone — re-cloneable from =https://github.com/budavariam/traverse_facebook_galleries.git=, branch =master=; recorded here so the proof survives the deletion). -- Consequences: easier — =~/projects/= reaches the clean end state (home + work); harder — website's 11 open tasks stay in their own todo.org, outside the unified prioritization (acceptable: they're code tasks, not life tasks). - -** D3 — Unified todo.org: one file, per-area top-level sections -- State: accepted -- Context: cross-area prioritization wants one surface; the staleness script, agenda, and review workflows all operate on one file today. -- Decision: We will keep a single =todo.org= with =* <Area> Open Work= top-level sections mirroring =* Home Open Work=, unified under home's A-D priority scheme, with area tags on every imported task. -- Consequences: easier — one review rotation, one grep, one agenda file covers everything; harder — the file grows to roughly 5-6k lines (~110 incoming open tasks), so reads lean on Grep/offset and the section discipline matters more. - -** D4 — Per-area task triage at fold time -- State: accepted -- Context: each project graded priorities against siblings only; merging without re-grading would make cross-area priorities meaningless. -- Decision: We will walk each incoming area's open tasks with Craig at fold time, re-grading to the unified scheme (the task-review walk shape, applied per area). -- Consequences: easier — the unified list is trustworthy from day one; harder — the big folds (finances at 43 tasks) cost a real review session each. - -** D5 — Cooling-off before any destruction -- State: accepted -- Context: "if it goes south, I need a way to restore." -- Decision: We will destroy nothing for 30 days after the final fold: source dirs go to =~/projects/.retired/=, server bares stay, snapshots and tags persist. fb-photo-scraper deletion (D2) is the one exception — it's an unmodified upstream clone. -- Consequences: easier — every layer of the restore path stays live through the risky window; harder — ~2G of retired duplicates sit on disk for a month. - -* Implementation phases - -Each phase ends with a working tree, a pushed commit, and a verification gate. One project per session is the expected pace; phases 3+ are repetitions of the runbook proven in phase 2. - -** Phase 0 — Pre-flight (global prep; gates per project at its turn) -Install =git-filter-repo=. Snapper snapshot + memory-dir tar. Tag and push =pre-consolidation= on home. - -The *live inventory gate* lives at =docs/consolidation-manifest-inventory.org= and is regenerated *per project, immediately before that project's fold* — not all at once. Craig keeps using not-yet-folded projects (staged freeze), so a single up-front table would go stale by Phase 3; the per-fold regeneration is the gate. Fields per project: default branch, origin URL, dirty count (=git status --porcelain=), ahead/behind vs upstream, inbox file count, =session-context.org= presence, memory file count, project-workflow/-script names (collision candidates), and disposition (fold / relocate / delete / out-of-scope). The gate passes only when: clean tree, ahead/behind 0/0, inbox empty, no live session-context. A failing project gets fixed (wrap, commit, process, push) and its row regenerated before its fold begins. - -D2 is resolved (2026-06-11); no open decisions remain in this phase. - -** Phase 1 — Pilot fold: philosophy -Smallest life project, no todo.org, no memories, empty inbox. Run the full fold runbook (git merge + redistribution + manifest + verification). Then the *rollback drill*: in a disposable =--no-local= clone of home (or a throwaway branch), run the Mode-B removal runbook against the pilot's manifest and verify the folded state is fully gone — sessions, workflows, =<name>/= tree. Discard the clone. The legal and financial folds must never be the first test of the removal story. This phase hardens the runbook appendix; expect to amend the spec from what's learned (history entry, not rewrite). - -** Phase 2 — Dress rehearsal: clipper -Nearly as small (23M, no memories, empty inbox) but adds the one runbook path the pilot can't exercise: the todo.org import — =* Clipper Open Work= section, =:MIGRATED_FROM:= markers, and a one-task triage with Craig. After this phase every runbook step has run at least once except the memory merge (premieres in Phase 3; lowest-risk step — plain file copies outside git, tar-backed). - -** Phase 3 — jr-estate -The priority fold. 704M history, 18-task triage, 44 sessions, and the first memory merge (7 files). One session. - -** Phase 4 — danneel -613M history, 10-task triage, 45 sessions, 1 project-workflow. One session. - -** Phase 5 — finances -251M history and the heaviest triage (43 tasks). One session, possibly two if the triage runs long. - -** Phase 6 — Remaining folds + code relocations (together) -Fold documents, elibrary, health, kit (~36 incoming tasks, elibrary/health/kit memories, kit's 4 project-workflows collision-checked). Move website and little-elisper to =~/code/= (mv + memory-dir rename per the homelab→home runbook); delete fb-photo-scraper (origin recorded in D2). After this phase =~/projects/= contains home, work, and =.retired/=. - -** Phase 7 — Ecosystem pass -Fix every absolute-path reference (emacs config, org-roam, agenda-files, bookmarks, rulesets docs naming folded projects as inbox-send/cross-agent targets). Migrate velox (pull home, retire its clones). Write the KB node recording the new layout. Start the 30-day cooling clock; file a dated vNext task for server bare archival and =.retired/= deletion. - -* Acceptance criteria - -- [ ] =~/projects/= contains exactly =home=, =work=, and =.retired/=. -- [ ] For each folded project, =git log --oneline <name>/ | tail= in home shows its earliest original commits. -- [ ] Manifest parity per fold: every path in the source's =git ls-files= listing exists under =home/<name>/= or appears in the manifest's redistribution map; every untracked/ignored/inbox file has a recorded disposition. Path-list comparison, not counts. -- [ ] =todo.org= passes org-lint; every imported task carries an area tag and an A-D priority Craig re-graded; imported sections carry =:MIGRATED_FROM:= markers. -- [ ] =task-review-staleness.sh --list todo.org 20= run after each fold surfaces the imported area's tasks as depth-2 review units alongside existing areas (proves the rotation spans the whole list). -- [ ] Per fold: source memory basenames diffed against home's memory dir and =MEMORY.md= entries — all accounted for; source memory dirs are in the backup tar. -- [ ] Link-rewrite check per fold: the before-grep count is recorded in the manifest, and the after-grep over =~/.emacs.d ~/sync/org ~/org/roam ~/projects/home= returns only hits classified historical (session archives, this spec) — zero live links. -- [ ] Layer-1 restore drill passes: clone one folded project from its untouched server bare into =/tmp=, confirm it's whole. -- [ ] Mode-B rollback drill (Phase 1 pilot) passes: the pilot fold is fully removable from a disposable clone using only its manifest. -- [ ] A fresh Claude session in home can answer "what are my top 5 tasks across all areas?" from the unified todo.org. -- [ ] velox runs a clean session in home post-migration with no stale-remote errors. - -* Readiness dimensions - -- Data model & ownership: every file keeps its owner (Craig); =.ai/= state redistributes per the merge map above; memory dirs are the one store outside git — covered by the tar in Phase 0 and the copy step per fold. -- Errors, empty states & failure: every fold step is git-tracked, so a failed fold is =git reset --hard <pre-fold tag>= plus re-running from the temp clone (which is rebuilt from scratch each attempt). filter-repo failures abort before anything touches home. -- Security & privacy: all content stays on the private cjennings.net remote; no new exposure surface. The merged repo concentrates sensitive material (legal + financial + health) in one clone — same machines, same threat model as today. -- Observability: each fold is one merge commit + one redistribution commit, tagged; progress is the phase checklist in todo.org; verification gates are the acceptance criteria run per-fold. -- Performance & scale: ~1.8G final =.git=; clone cost noted. todo.org at 5-6k lines stays well within Grep/offset workflows. No runtime performance surface. -- Reuse & lost opportunities: reuses the homelab→home rename runbook (memory-dir rename, link sweep), the task-review walk for triage, snapper for snapshots, and the established area-dir pattern. git-filter-repo over hand-rolled rewrites. -- Architecture fit & weak points: area dirs match the working-files convention. Weak point: the =.ai/= redistribution is manual and per-project — mitigated by the pilot phase hardening a written runbook before the critical folds. -- Config surface: none — no knobs. The one dependency is the =git-filter-repo= package. -- Documentation plan: this spec is the migration doc; the fold runbook and manifest template live in the appendix below (refined by the Phase 2 pilot); the KB node in Phase 6 records the end state for all future agents. -- Dev tooling: N/A because the migration is one-shot; the runbook commands in Design are the tooling. -- Rollout, compatibility & rollback: staged per-project rollout, multi-machine sequencing (velox last), layered rollback (snapshot / untouched bares / tags / retired dirs), 30-day cooling before any destruction. Dry-run equivalent: the pilot fold. -- External APIs & deps: =git-filter-repo= (AUR, stable, widely used — verify installed in Phase 0). No network APIs. - -* Risks, Rabbit Holes, and Drawbacks - -- /Link rot is the long tail./ Absolute =file:= links to old project paths can lurk in org-roam, emacs bookmarks, calendar event descriptions, and Keep notes. The Phase 6 grep covers the file-based stores; Keep and calendar references can't be grepped — accept that stragglers get fixed on encounter. -- /todo.org scale./ 5-6k lines is fine for tools, but the agenda view gets dense. If it becomes noise, the vNext escape hatch is per-area =#+CATEGORY= or splitting resolved sections to an archive file — not re-splitting projects. -- /Triage fatigue./ Re-grading ~110 tasks is the human bottleneck. Mitigation: it's split across the fold phases, and each area's walk uses the existing 7-at-a-time review muscle. -- /Workflow collisions./ 13 project-workflow files across sources; names look distinct but the check is mandatory per fold. -- /The merged repo is a bigger blast radius./ A bad force-push or corrupting operation now touches everything. Mitigation: the same layered backups, plus home already carries this responsibility for its own content. -- /Drawback accepted:/ per-project session isolation disappears — one project's noisy session history now shares a dir with everything. The area prefix on archived session names keeps provenance. - -* Appendix — Fold runbook (per project) - -Refined by the Phase 2 pilot; until then this is the v0 contract. Every step either succeeds with the expected output or the fold stops — no improvising past a failed step. - -1. /Gate./ Regenerate the project's row in the live inventory (Phase 0 fields). Require: clean =git status --porcelain=, ahead/behind 0/0, inbox empty, no =session-context.org=. Fix and regenerate, or stop. -2. /Manifest open./ Create =docs/consolidation-manifest-<name>.org= from the template below; fill source state and the =git ls-files= listing; inventory untracked/ignored files with dispositions. The Redistribution row reads "the commit introducing this manifest" — a commit sha can't be embedded in its own commit (pilot learning, 2026-06-11); the merge sha is known beforehand and is recorded literally. -3. /Tag./ =git tag pre-fold-<name> && git push origin pre-fold-<name>=. -4. /History fold./ The filter-repo + merge block from Design (with =--no-local=, =$branch=, no =--force=). Record the merge sha in the manifest. -5. /Redistribute./ Steps 1-8 of the =.ai/= and task merge map, recording each move in the manifest's redistribution map as it happens. One commit; record its sha. -6. /Verify./ Manifest parity (path lists), org-lint on todo.org, staleness-script check, memory diff, link before/after grep. All green or the fold stops here for repair. -7. /Retire./ =mv ~/projects/<name> ~/projects/.retired/<name>=; record the path. Push home. - -** Manifest template - -#+begin_example -,#+TITLE: Consolidation manifest — <name> -| Source path | ~/projects/<name> | -| Origin | <url> | -| Branch / HEAD | <branch> / <sha> | -| Gate state | clean / 0-0 / inbox 0 / no session-context | -| Merge commit | <sha> | -| Redistribution | <sha> | -| Retired to | ~/projects/.retired/<name> | - -,* Tracked universe -<git ls-files output, or sha256 + appendix> - -,* Untracked / ignored / inbox dispositions -| file | disposition (processed / moved-to / archived / dropped) | - -,* Redistribution map -- Sessions: <old> → <new> … -- todo.org: section ":MIGRATED_FROM: <name>" added at <heading> -- Workflows/scripts copied: <names + collision resolutions> -- Memory: <files copied> + MEMORY.md lines added -- Link rewrites: <file:line before → after> - -,* Link grep -- Before: <count> | After: <count, all classified historical> -#+end_example - -* Review dispositions - -Findings from the 2026-06-11 Codex review (review file deleted on processing per spec-response). Modified items below; *everything else was accepted as written* — H1 (manifest + redistribution-aware restore), H2 (path-list verification, porcelain gate, find-prune fix by removal), H3 (=--no-local=, no =--force=), H4 (live inventory gate), M2 (pilot rollback drill), M3 (fb-photo-scraper re-clone pointer), the UX provenance markers, the documentation appendix, and the memory/link verification commands. - -- /M1 (memory tar metadata) — modified:/ the review offered preserving metadata or declaring content-only sufficient. Chose content-only: memory files are plain-text markdown the harness reads by path; no permissions/ACL/xattr metadata is load-bearing. Stated in Layer 0 rather than adding =--xattrs --acls=. -- /Test strategy item 2 (staleness fixture test) — modified:/ a live =task-review-staleness.sh --list todo.org 20= check after each fold replaces a new fixture-based unit test. The script already has its own bats suite; the migration-specific question ("are imported area tasks depth-2 review units?") is answered better by the live check on the real file, per fold, than by a one-shot fixture. -- /Open question 2 (revert vs manifest-removal as the supported runbook) — modified:/ the "choose one" framing doesn't survive the time axis. Supported path: revert both commits (redistribution first) while the fold is recent; once shared files have moved on and reverts conflict, the manifest-driven removal commit is the path. Both are now written in Restore Mode B; the manifest makes the fallback safe, which is why it exists. - -* Review and iteration history - -** 2026-06-11 Thu @ 15:11:32 -0500 — Claude Code (home, with Craig) — author -- What changed: re-sequenced the implementation phases to Craig's chosen order — philosophy pilot, clipper dress rehearsal (added as its own phase so the todo.org-import path is proven before real data), then jr-estate → danneel → finances by urgency, with the remaining folds + code relocations merged into one closing phase before the ecosystem pass. Phase 0's live inventory gate is now explicitly per-project-at-its-turn, matching the staged-freeze approach (Craig keeps using not-yet-folded projects until their turn). -- Why: Craig wants the critical legal/financial projects consolidated early after a proven runbook, and chose staged freeze over a full shutdown. The clipper rehearsal closes the gap where the pilot (no todo.org) never exercises task import. -- Artifacts: todo.org phase tasks re-sequenced to match. - -** 2026-06-11 Thu @ 14:13:49 -0500 — Codex — reviewer -- What changed or was recommended: assigned =Ready= after re-running spec-review against the incorporated spec; no further blocking review notes and no new review file. -- Why: the prior blockers are now covered by the per-fold manifest contract, live inventory gate, =--no-local= filter-repo runbook, redistribution-aware restore, Phase 2 rollback drill, and manifest-based acceptance criteria. -- Artifacts: this spec; [[file:../todo.org::*Project consolidation into home][todo.org tracking task]] updated with Ready status and implementation phase tasks. - -** 2026-06-11 Thu @ 13:20:54 -0500 — Claude Code (home) — responder -- What changed: all four blocking findings accepted and woven in — =--no-local= + no-=--force= runbook with a =$branch= variable (H3, H4's master/main catch), a Per-fold manifest section as the restore/verification contract (H1, H2), two-mode single-project restore covering the redistribution commit (H1), Phase 0 live inventory gate (H4), Phase 2 Mode-B rollback drill (M2), manifest-parity acceptance criteria replacing file counts (H2), fb-photo-scraper re-clone pointer in D2 (M3), =:MIGRATED_FROM:= provenance markers (UX), runbook appendix + manifest template (docs). Three points modified with reasons in Review dispositions; nothing rejected. -- Why: the review's core finding was right — restore and verification only covered the history merge, not the redistribution commit and the untracked-file universe. The manifest is the single artifact that fixes both. -- Artifacts: review file (deleted on processing); dispositions section above; todo.org tracking task updated. - -** 2026-06-11 Thu @ 13:09:29 -0500 — Codex — reviewer -- What changed or was recommended: assigned =Not ready= and wrote a blocking review focused on exact rollback semantics, per-fold manifests, live inventory gating, =git clone --no-local= for filter-repo safety, and stronger verification than raw file counts. -- Why: the design direction is sound, but implementation would still require inventing how to unwind redistributed =.ai/=, =todo.org=, inbox, and memory state safely after each fold. -- Artifacts: review file deleted during the response pass; retained via the dispositions section above. - -** 2026-06-11 Thu @ 12:08:03 -0500 — Claude (with Craig) — author -- What: initial draft. -- Why: Craig asked for a consolidation design with restore guarantees — one prioritization surface for all personal projects. -- Artifacts: survey data gathered live from ~/projects on ratio; todo.org task cross-linked. diff --git a/inbox/PROCESSED-2026-06-11-1705-from-home-addendum-to-today-s-consolidation.org b/inbox/PROCESSED-2026-06-11-1705-from-home-addendum-to-today-s-consolidation.org deleted file mode 100644 index 392b844..0000000 --- a/inbox/PROCESSED-2026-06-11-1705-from-home-addendum-to-today-s-consolidation.org +++ /dev/null @@ -1,5 +0,0 @@ -#+TITLE: Addendum to today's consolidation handoff: first concrete to -#+SOURCE: from home -#+DATE: 2026-06-11 17:05:20 -0500 - -Addendum to today's consolidation handoff: first concrete tooling edge case found. todo-cleanup.el --archive-done assumes exactly one level-1 'Open Work' and one 'Resolved' heading per todo.org; home's consolidated file now has per-area pairs (Home Open Work / Home Resolved, Clipper Open Work / Clipper Resolved, more coming) and the pass skips with 'more than one level-1 heading contains Open Work'. Suggested fix: match each '* <Area> Open Work' with its '* <Area> Resolved' sibling and archive within the pair, falling back to current behavior for single-pair files. Until then home archives manually at wrap-up. diff --git a/inbox/PROCESSED-2026-06-11-1755-from-work-from-the-work-project-2026-06-11-craig.org b/inbox/PROCESSED-2026-06-11-1755-from-work-from-the-work-project-2026-06-11-craig.org deleted file mode 100644 index cbd8241..0000000 --- a/inbox/PROCESSED-2026-06-11-1755-from-work-from-the-work-project-2026-06-11-craig.org +++ /dev/null @@ -1,7 +0,0 @@ -#+TITLE: From the work project, 2026-06-11: Craig's guidance on triag -#+SOURCE: from work -#+DATE: 2026-06-11 17:55:46 -0500 - -From the work project, 2026-06-11: Craig's guidance on triage-intake reporting, for the canonical triage-intake.org engine's Render/summary section. Sweep summaries should report DELTAS ONLY: a new invite, a new/moved/cancelled calendar event, a new message needing attention. A sweep where nothing changed renders as one line (e.g. '17:39 sweep: no changes'), never a per-source 'quiet' roll-call. His words: 'we only need to report if anything's changed when we do triage intake. did someone send me a new invite? did christine throw something on my calendar that wasn't there earlier? did someone cancel a meeting?' Failures still surface loudly per the existing engine rule (never folded into the no-change line), and the suggested-actions queue line stays. The work project is applying this immediately; please fold into the canonical engine so all projects pick it up on template sync. - -Addendum (same day, 17:55 CDT): Craig also ruled that Telegram dev-community group traffic (zed, GNU Emacs, Kitty, etc.) is skipped in sweep reports entirely — not even the FYI name+count line the telegram plugin's Render currently specifies — unless he specifically asks. Real DMs from known contacts still surface as Action. Please update triage-intake.telegram.org's Render section accordingly. diff --git a/inbox/PROCESSED-2026-06-11-1823-from-.emacs.d-memory-sweep-phase-1-5-complete-for.org b/inbox/PROCESSED-2026-06-11-1823-from-.emacs.d-memory-sweep-phase-1-5-complete-for.org deleted file mode 100644 index b7ea37c..0000000 --- a/inbox/PROCESSED-2026-06-11-1823-from-.emacs.d-memory-sweep-phase-1-5-complete-for.org +++ /dev/null @@ -1,5 +0,0 @@ -#+TITLE: Memory sweep (Phase 1.5) complete for dotemacs (~/.emacs.d), -#+SOURCE: from .emacs.d -#+DATE: 2026-06-11 18:23:38 -0500 - -Memory sweep (Phase 1.5) complete for dotemacs (~/.emacs.d), 2026-06-11. Inventory: 7 memories. Promoted to KB: 3 (no-make-frame-in-live-daemon, proton-bridge-headless-cert-mismatch, open-images-with-imv — pushed in roam commit a915760). Stayed local: 3 (commit-flow-no-approval-gate — Craig scoped it per-project, explicitly not KB; color-sorting-research and theme-design-render-format — theme-scoped, held local at Craig's call, with the palette-columns spec possibly superseding LCCL soon). Deleted: 1 (numbered-options-with-recommendation-first — superseded by the canonical interaction.md rule). diff --git a/inbox/PROCESSED-2026-06-11-1909-from-home-inbox-response-consolidation-and-todo.org b/inbox/PROCESSED-2026-06-11-1909-from-home-inbox-response-consolidation-and-todo.org deleted file mode 100644 index e920dfd..0000000 --- a/inbox/PROCESSED-2026-06-11-1909-from-home-inbox-response-consolidation-and-todo.org +++ /dev/null @@ -1,25 +0,0 @@ -#+TITLE: Home reply: folds resuming + todo.org shape decided — single pair, kill the multi-pair fix -#+DATE: 2026-06-11 - -Replying to both of your 2026-06-11 handoffs (consolidation okay 1708, todo-shape heads-up 1716). - -* Folds resuming - -Confirmed received — the HOLD is lifted and Phase 3 (jr-estate) is clear to start. Thanks for the tooling sweep and the Phase 7 reference list; the list is folded into our ecosystem-pass task so the link sweep cross-checks your fixes. - -On your ask: the session archives are already covered by design. Redistribution step 1 merges each source's .ai/sessions/ into home's .ai/sessions/ with the area name inserted into the filename, and both pilots did exactly that (philosophy 5 files, clipper 6). Nothing for session-harvest to lose — it'll see the history as home's, area-prefixed. - -* todo.org shape: single pair wins - -Craig confirmed the single-pair shape in tonight's home session, and the reshape is already done — only clipper's import was in (an empty open section plus 3 resolved entries), so it cost a few minutes now versus a real migration after jr-estate and finances. - -What landed on our side: - -- todo.org holds one Home Open Work / Home Resolved pair. Clipper's imported tasks moved under Home Resolved, each carrying its own :MIGRATED_FROM: clipper / :MIGRATED_ON: drawer plus a :clipper: tag. The per-area level-1 sections are dissolved. -- Spec amended: D3 (decision + amendment note), task-merge step 2 (append under the home pair, per-task provenance), restore Mode B path 2 (excision is a targeted :MIGRATED_FROM: property sweep; the manifest lists imported headings individually). -- The clipper manifest is amended with the reshape and the individual imported headings, so its Mode-B contract stays honest. - -* What this decides for you - -- Kill the todo-cleanup.el multi-pair archive [#B] — the single-pair file works with the existing tooling unmodified, which was half the argument for the shape. -- No staleness-pool changes needed. Imported tasks join the unified A-C pool on their own merits once re-graded at fold-time triage; area tags are just tags. The existing convention stands: [#D] imports sit outside the A-C pool by design. diff --git a/inbox/PROCESSED-2026-06-11-1951-from-home-inbox-response-jr-estate-memory-sweep.org b/inbox/PROCESSED-2026-06-11-1951-from-home-inbox-response-jr-estate-memory-sweep.org deleted file mode 100644 index ebaeff0..0000000 --- a/inbox/PROCESSED-2026-06-11-1951-from-home-inbox-response-jr-estate-memory-sweep.org +++ /dev/null @@ -1,12 +0,0 @@ -#+TITLE: jr-estate memory sweep complete — 2 promoted / 3 kept / 2 deleted (via the home fold) -#+DATE: 2026-06-11 - -Answering your 2026-06-10 migrate-memories handoff to jr-estate. The sweep ran inside jr-estate's fold into home (Phase 3 of the consolidation, completed tonight), since the fold's memory-merge step is the same walk. - -Counts, Craig-approved at fold-time triage: - -- Promoted 2 to ~/org/roam/agents/ (commit 45d8e6c, pushed): the forms name-with-number preference (always pair a form's id with its full name) and the PDF-editing tooling split (Xournal++ for Craig, pdftools-venv overlay edits for Claude, signatures always through Craig). -- Kept 3 local, now in home's memory dir with jr-estate attribution: aj-fudge (who AJ is), bond-waiver-conditions, chevron-stock-holding — estate-scoped facts. -- Deleted 2: default-email-cmail (rule-encoded in protocols.org's email table) and feedback-no-same-day-scheduling (duplicate of home's existing no-scheduling-for-today memory). - -jr-estate is now a home area; its future durable facts flow through home's capture-then-promote discipline. Its 44 session archives merged into home's .ai/sessions/ area-prefixed, so session-harvest's first run will see them. diff --git a/inbox/PROCESSED-2026-06-11-2154-from-home-inbox-response-finances-memory-sweep.org b/inbox/PROCESSED-2026-06-11-2154-from-home-inbox-response-finances-memory-sweep.org deleted file mode 100644 index a3bed46..0000000 --- a/inbox/PROCESSED-2026-06-11-2154-from-home-inbox-response-finances-memory-sweep.org +++ /dev/null @@ -1,8 +0,0 @@ -#+TITLE: finances memory sweep complete — 0 promoted / 1 kept / 0 deleted (via the home fold) -#+DATE: 2026-06-11 - -Answering your 2026-06-10 migrate-memories handoff to finances. The sweep ran inside finances' fold into home (Phase 5 of the consolidation). - -Counts: promoted 0; kept 1 local in home's memory dir with finances attribution (rosalea-daly-passed — contact guidance scoped to the Strata Trust SDIRA workstream, no cross-project value); deleted 0. - -finances is now a home area; its 24 session archives merged into home's .ai/sessions/ area-prefixed for session-harvest. diff --git a/inbox/PROCESSED-2026-06-11-2308-from-home-lint-org-el-false-positive-mu4e-msgid.org b/inbox/PROCESSED-2026-06-11-2308-from-home-lint-org-el-false-positive-mu4e-msgid.org deleted file mode 100644 index 585ae4d..0000000 --- a/inbox/PROCESSED-2026-06-11-2308-from-home-lint-org-el-false-positive-mu4e-msgid.org +++ /dev/null @@ -1,5 +0,0 @@ -#+TITLE: lint-org.el false positive: mu4e:msgid: links flag as invali -#+SOURCE: from home -#+DATE: 2026-06-11 23:08:59 -0500 - -lint-org.el false positive: mu4e:msgid: links flag as invalid-fuzzy-link in batch runs. The mu4e link type is registered by mu4e at runtime in a live Emacs, so batch org-lint parses [[mu4e:msgid:...]] as a fuzzy heading ref and reports 'Unknown fuzzy location'. Eight such links in home's todo.org survived a full lint pass tonight as the only remaining judgment items — all work fine interactively. Suggested fix in lint-org.el: register the link type as a no-op before linting, e.g. (org-link-set-parameters "mu4e"), or add a suppressed-categories entry for invalid-fuzzy-link items whose target starts with a known runtime link prefix (mu4e:, possibly others like attachment:). Same pattern as the existing verbatim-asterisk suppression. diff --git a/inbox/PROCESSED-2026-06-12-0101-from-.emacs.d-page-signal-is-broken-the-dedicated.org b/inbox/PROCESSED-2026-06-12-0101-from-.emacs.d-page-signal-is-broken-the-dedicated.org deleted file mode 100644 index 30a680c..0000000 --- a/inbox/PROCESSED-2026-06-12-0101-from-.emacs.d-page-signal-is-broken-the-dedicated.org +++ /dev/null @@ -1,5 +0,0 @@ -#+TITLE: page-signal is broken: the dedicated pager account (+1504517 -#+SOURCE: from .emacs.d -#+DATE: 2026-06-12 01:01:58 -0500 - -page-signal is broken: the dedicated pager account (+15045173983, the Claude Pager Google Voice number registered with signal-cli) reports 'User ... is not registered' on every send, including with explicit --to. Signal appears to have deregistered the account (GV numbers get periodically re-verified). Re-registration needs Craig (captcha/SMS). Discovered 2026-06-12 when the dotemacs config-audit completion page failed; fallback used email. Wrapper: claude-templates/bin/page-signal. diff --git a/inbox/PROCESSED-2026-06-12-0207-from-home-memory-sweep-reply-for-the-2026-06-10.org b/inbox/PROCESSED-2026-06-12-0207-from-home-memory-sweep-reply-for-the-2026-06-10.org deleted file mode 100644 index 72e459b..0000000 --- a/inbox/PROCESSED-2026-06-12-0207-from-home-memory-sweep-reply-for-the-2026-06-10.org +++ /dev/null @@ -1,5 +0,0 @@ -#+TITLE: Memory-sweep reply for the 2026-06-10 migrate-memories hando -#+SOURCE: from home -#+DATE: 2026-06-12 02:07:49 -0500 - -Memory-sweep reply for the 2026-06-10 migrate-memories handoff, covering elibrary, health, and kit (all three were folded into home as areas on 2026-06-11, so the sweep ran at fold time with Craig's approval; counts are promoted / kept local / deleted). elibrary: 0 / 0 / 2 — private-remote fact duplicates home's git-hosting-privacy-model memory; project-scripts convention is encoded in startup.org. health: 0 / 0 / 1 — scheduling feedback duplicates home's no-scheduling-for-today memory. kit: 1 / 0 / 2 — feedback-hand-prep-items-to-work-inbox promoted into home's memory (operative for home's wrap-up extension); no-default-today-scheduling duplicates the same home memory; no-emphasis-formatting-in-prose is rule-encoded in /voice prose mode. Nothing went to the org-roam KB — no swept fact met the durable cross-project bar that wasn't already encoded in rules or home memory. All source files preserved in the pre-consolidation memory tar. The home, documents, and remaining-area sweeps are covered by home's own session discipline going forward. diff --git a/inbox/PROCESSED-2026-06-28-2301-from-home-adopted-home-s-todo-org-priority-scheme.org b/inbox/PROCESSED-2026-06-28-2301-from-home-adopted-home-s-todo-org-priority-scheme.org deleted file mode 100644 index 3bbd7dc..0000000 --- a/inbox/PROCESSED-2026-06-28-2301-from-home-adopted-home-s-todo-org-priority-scheme.org +++ /dev/null @@ -1,5 +0,0 @@ -#+TITLE: Adopted: home's todo.org Priority Scheme now carries the sev -#+SOURCE: from home -#+DATE: 2026-06-28 23:01:35 -0400 - -Adopted: home's todo.org Priority Scheme now carries the severity × frequency bug-priority matrix as a 'Codebase bug priority' subsection, with Critical/Major/Minor/Cosmetic and the frequency rows defined for home's codebase (the finances/ plain-text-accounting pipeline). Matrix structure and the fixed P1->[#A]...P4->[#D] mapping kept verbatim; severity-alone carve-out included for financial-data leaks. Re-grade of existing :bug: tasks was a no-op — the only :bug: heading is CANCELLED. No further action needed. diff --git a/inbox/PROCESSED-2026-07-04-1302-from-home-task-for-rulesets-document-and-decide.org b/inbox/PROCESSED-2026-07-04-1302-from-home-task-for-rulesets-document-and-decide.org deleted file mode 100644 index 1abc1a6..0000000 --- a/inbox/PROCESSED-2026-07-04-1302-from-home-task-for-rulesets-document-and-decide.org +++ /dev/null @@ -1,5 +0,0 @@ -#+TITLE: Task for rulesets: document (and decide ownership of) the Si -#+SOURCE: from home -#+DATE: 2026-07-04 13:02:07 -0500 - -Task for rulesets: document (and decide ownership of) the Signal pager. Context: home retired the ntfy phone-notification channel (phone-notify/phone-recv, self-hosted ntfy on ratio) on 2026-07-04 in favor of paging over Signal, and tore the ntfy system down. But the Signal pager isn't documented anywhere — no pager script in ~/.local/bin, and the notify script doesn't reference Signal. What exists on ratio: signal-cli 0.14.5, configured with account 404211. The interface (a send wrapper, how a workflow pages Craig, how replies are read) is uncaptured, so no session can actually use the channel yet. This is the successor to the ntfy tooling's rulesets-ownership question (the 6/17 two-way-comms proposal): a phone paging channel is cross-machine tooling, so its canonical home + docs belong in rulesets. Suggested deliverable: a documented Signal pager (send + read-replies), the signal-cli setup/account notes, and the sync path — the Signal equivalent of what the retired ntfy runbook covered. Craig flagged this as a task for rulesets to finish. diff --git a/inbox/PROCESSED-2026-07-05-0420-from-archsetup-proposal-incoming-ui-prototyping.org b/inbox/PROCESSED-2026-07-05-0420-from-archsetup-proposal-incoming-ui-prototyping.org deleted file mode 100644 index 480d006..0000000 --- a/inbox/PROCESSED-2026-07-05-0420-from-archsetup-proposal-incoming-ui-prototyping.org +++ /dev/null @@ -1,5 +0,0 @@ -#+TITLE: Proposal incoming (ui-prototyping-process-proposal.org): a U -#+SOURCE: from archsetup -#+DATE: 2026-07-05 04:20:42 -0500 - -Proposal incoming (ui-prototyping-process-proposal.org): a UI/UX prototype process for specs with a non-trivial UI — research-first during brainstorming, then ~5 full working prototype directions, iterate one to final, name <spec-name>-prototype-<N>.html, link final in the spec + keep old iterations in the spec history. Worked example is archsetup's timer-panel spec + its 3 prototypes. Suggested it fold into spec-create/spec-review or a new ui-prototyping rule — your value gate decides placement. diff --git a/inbox/PROCESSED-2026-07-05-0420-from-archsetup-ui-prototyping-process-proposal.org b/inbox/PROCESSED-2026-07-05-0420-from-archsetup-ui-prototyping-process-proposal.org deleted file mode 100644 index e0677eb..0000000 --- a/inbox/PROCESSED-2026-07-05-0420-from-archsetup-ui-prototyping-process-proposal.org +++ /dev/null @@ -1,79 +0,0 @@ -#+TITLE: Proposal — UI/UX prototype process for specs with a non-trivial UI -#+AUTHOR: Craig Jennings (via archsetup session) -#+DATE: 2026-07-05 - -* Intro / why this is coming to you - -Working the timer-panel spec in archsetup, we found the right way to settle a -UI design: research first, then build a handful of full working prototypes, -then iterate one to a final — all before committing GTK code. It worked well -enough that Craig wants it as a standing part of the spec process for any spec -whose deliverable has a non-trivial UI. This is the write-up, proposed for the -rulesets layer (spec-create / spec-review, or a new =ui-prototyping= rule — -your call on placement). - -Worked example living now in archsetup: =docs/specs/2026-07-02-timer-panel-spec.org= -plus =docs/prototypes/2026-07-02-timer-panel-prototype-{1,2,3}.html=. The spec's -"Prototype iterations" subsection and its new design decisions show the shape in -practice. - -* The process - -** 1. Trigger — non-trivial UI only -Applies when a spec's deliverable is a real UI: a panel, a multi-control -surface, a visual layout with interacting parts. Not a single dialog, a CLI -flag, or a one-off prompt. If "which of these layouts is right?" can't be -answered from a sentence, it qualifies. - -** 2. Research first — during brainstorming, before prototyping -Before any prototype, survey how existing and best-in-class tools solve the same -UX and functionality (the category's well-regarded apps, prior art, conventions -users already expect). Feed the findings into the spec's Goals and Design so the -UX and functionality are understood *before* a single prototype. Prototyping -blind wastes iterations re-deriving what a 20-minute survey would have told you. -Cite the sources in the spec. - -** 3. Brainstorm the UX + functionality in the spec -Informed by the research, write the goals, the interactions, and the functional -surface into the spec. This is the "what and why" the prototypes will make real. - -** 4. Prototype — ~5 initial directions, then iterate to a final -Build about five *distinct directions* (genuinely different layouts / -interaction models, not variations of one) as full working prototypes over one -shared engine, in the project's design language. Pick a direction, then iterate -*that one* across numbered passes to the final design. Each meaningful pass is -saved as its own numbered prototype so the design history is walkable. - -** 5. Full working prototypes, not mockups -The prototypes must be *functional* — real state, real controls, real behavior — -so decisions are made against how it feels to use, not against a picture. A -static mockup hides the interaction problems that only surface when you drive it. - -** 6. Naming + location -=docs/prototypes/<spec-name>-prototype-<N>.html=, where =<spec-name>= is the -spec's dated slug (dropping the =-spec= suffix) and =N= is the iteration number. -E.g. for =2026-07-02-timer-panel-spec.org= → -=2026-07-02-timer-panel-prototype-1.html=, =-2.html=, =-3.html=. - -** 7. Link from the spec; keep old iterations in history -The spec links the *final* prototype in its design section, and keeps links to -*every* prior iteration in a "Prototype iterations" subsection under the status -heading — newest last — so the design's evolution is walkable from the spec. - -** 8. Decisions get written down once seen working -A design decision is recorded in the spec's Decisions only after it's been seen -working in a prototype. "Resolved live through the prototype iteration" — the -prototype is the evidence. - -* Suggested placement (your value gate decides) - -- =spec-create=: for a non-trivial-UI spec, add a "research → brainstorm → - prototype (5 directions → iterate)" step, and require the "Prototype - iterations" subsection. -- =spec-review=: for a non-trivial-UI spec, verify the prototype process ran — - research cited, final prototype linked, iterations in history, decisions - backed by a prototype. -- Or a standalone =claude-rules/ui-prototyping.md= that both workflows point at. - -Not prescribing which — sending the content and the worked example; apply the -rulesets value gate and place it where it fits. diff --git a/inbox/PROCESSED-2026-07-06-1054-from-archsetup-off-workspace-captures-rule.md b/inbox/PROCESSED-2026-07-06-1054-from-archsetup-off-workspace-captures-rule.md deleted file mode 100644 index 03538af..0000000 --- a/inbox/PROCESSED-2026-07-06-1054-from-archsetup-off-workspace-captures-rule.md +++ /dev/null @@ -1,38 +0,0 @@ -# Proposal: never use the user's active workspace for agent windows/captures - -From an archsetup session (2026-07-06). Craig's request, verbatim intent: when I open an app or take a screenshot for my own verification, don't do it on his active workspace — put it somewhere that doesn't interrupt what he's doing. He then asked to make this a rule for everyone and send it to rulesets. - -## Why - -During the audio-panel work I repeatedly launched the GTK panel and `imv` on Craig's live desktop to screenshot and verify. Each one popped onto his current workspace and stole focus/attention mid-task. Agents doing visual verification on a user's live session shouldn't hijack the workspace the user is actively working in. - -## The rule (proposed text, ready to place) - -**Never open a window or take a screenshot on the user's active workspace.** When visual verification needs a real window on the user's live desktop, keep it off the workspace they're working in: - -- **Captures for your own verification** — render and grab the window off the user's physical screen, then tear it down. On Hyprland this is a virtual headless output (verified non-disruptive on ratio 2026-07-06 — the physical monitor stayed on its workspace, focused, throughout): - - ```sh - hyprctl output create headless # virtual output on its own workspace - setsid <app> >/tmp/x.log 2>&1 </dev/null & - addr=$(hyprctl -j clients | python3 -c 'import json,sys; print(next((c["address"] for c in json.load(sys.stdin) if c.get("class")=="<CLASS>"), ""))') - hyprctl dispatch movetoworkspacesilent "<ws-on-headless>,address:$addr" # silent = keeps the user's focus - grim -o HEADLESS-<n> /tmp/shot.png # capture the virtual output only - pkill -f '<app>$'; hyprctl output remove HEADLESS-<n> # tear down, restore the display - ``` - - Key constraint: `grim` captures a *visible output*, so a window merely parked on another Hyprland workspace can't be screenshotted — it must render on the headless (or another real) output. That's why a headless output, not just "another workspace," is the tool for self-captures. (A nested compositor — weston/cage/sway — is the alternative on non-Hyprland Wayland or when a headless output isn't available; it needs the compositor installed.) - -- **Showing the user something** — open it on a *separate* real workspace and tell them which one, so it never grabs their active workspace. They switch when ready. (Craig's viewer preference is `imv`; launch it through the compositor — `hyprctl dispatch exec "imv <files>"` — so it survives the agent's shell, not a bare `&` job that gets reaped.) - -- **Always clean up** — close the window and remove any headless output afterward; verify the user's display is restored (physical monitor back to its workspace, no orphan processes). - -The principle is environment-general (don't commandeer the user's active workspace for agent-side visual work); the recipe above is the Hyprland/Wayland implementation. Other environments implement the same principle with their own off-screen mechanism. - -## Placement suggestion (your call — "appropriate places") - -I'd lean toward a short standalone rule file (e.g. `claude-rules/desktop-capture.md`) since it's a distinct concern, cross-referenced from `verification.md` (it's part of how visual verification is done) and `interaction.md` (it's about not disrupting the user). It could instead be a section in `verification.md`. The `imv`/viewer preference and the "launch through the compositor" mechanic could also land wherever `emacs.md`'s screenshot note lives. Pick whatever fits the layer best. - -## Companion (local, already applied) - -Captured as archsetup auto-memory (`display-images-via-imv.md`) as the stopgap; this inbox note is the propagation to canonical per the cross-project rule for rulesets-owned changes. diff --git a/inbox/PROCESSED-2026-07-08-1124-from-work-proposal-triage-intake-personal-gmail.org b/inbox/PROCESSED-2026-07-08-1124-from-work-proposal-triage-intake-personal-gmail.org deleted file mode 100644 index 6fb315b..0000000 --- a/inbox/PROCESSED-2026-07-08-1124-from-work-proposal-triage-intake-personal-gmail.org +++ /dev/null @@ -1,5 +0,0 @@ -#+TITLE: Proposal: triage-intake.personal-gmail.org edit (copy sent a -#+SOURCE: from work -#+DATE: 2026-07-08 11:24:19 -0500 - -Proposal: triage-intake.personal-gmail.org edit (copy sent alongside this note). Two additions to the Scan section, both from a 2026-07-08 work-session investigation: (1) a warning that the Gmail MCP listMessages tool caps at maxResults=100 and exposes no pageToken parameter, so >100 unread piles silently truncate — with the date-slice walk (before:<oldest-day>, dedupe by id) as the recipe, and a note that resultSizeEstimate is unreliable (stuck at 201 while the real union exceeded 300); (2) a mandatory cheap backlog-residue probe each sweep (q="is:unread in:inbox before:<anchor-date>" maxResults=5) that loudly surfaces any pre-anchor unread instead of letting anchored sweeps claim 'no changes' over a window they never saw. Root cause this fixes: ~300 unread accumulated invisibly Jun 4 - Jul 4 because anchored scans never look behind the anchor and the 7/4 catch-up hit the 100 cap. Companion: the work project's project-owned triage-intake.deepsat-gmail.org got the same two additions directly (work tool names); no other plugins in the gmail family. The engine file needs no change. diff --git a/inbox/PROCESSED-2026-07-08-1124-from-work-triage-intake.personal-gmail.org b/inbox/PROCESSED-2026-07-08-1124-from-work-triage-intake.personal-gmail.org deleted file mode 100644 index ca81f5d..0000000 --- a/inbox/PROCESSED-2026-07-08-1124-from-work-triage-intake.personal-gmail.org +++ /dev/null @@ -1,68 +0,0 @@ -#+TITLE: Triage Intake — Personal Gmail Source -#+AUTHOR: Craig Jennings & Claude -#+DATE: 2026-05-26 - -# Source plugin for the triage-intake engine. See triage-intake.org for the -# contract and the Phase A-D orchestration. This file declares ONE source. - -* Source: personal-gmail -:PROPERTIES: -:ORDER: 20 -:ENABLED: mcp google-docs-personal present -:ANCHOR: epoch -:SUBAGENT_OVER: 50 -:END: - -** Scan - -Personal Gmail unread in the inbox since the anchor: - -#+begin_src text -mcp__google-docs-personal__listMessages q="is:unread in:inbox after:<anchor-epoch>" maxResults=100 -#+end_src - -⚠ *Express the cutoff as the literal UNIX epoch* — =after:1778856990=, not =after:YYYY/MM/DD=. Gmail's =after:YYYY/MM/DD= operator only supports day resolution; the =YYYY/MM/DD HH:MM:SS= form is NOT valid syntax — Gmail parses the space as a term separator, treats =HH:MM:SS= as a search term that never matches, and returns 0 results, silently masking unread mail. The engine supplies =<anchor-epoch>= because this source declares =ANCHOR: epoch=. - -⚠ *Do NOT add =-category:promotions -category:social=.* That filter masked 67 promo+social messages across two runs (2026-05-04, 2026-05-06), both needing a follow-up sweep. Pull the full unfiltered set; the trash-leaning bias in Classify handles promotions and social directly. - -⚠ *The MCP caps at =maxResults=100= and exposes NO =pageToken= parameter.* The response carries a =nextPageToken=, but the tool can't consume it, so a pile over 100 is silently truncated — the tail below the cap never gets classified, and every later anchored sweep skips it (it predates the new anchor). This is exactly how a 300+ backlog accumulated invisibly by 2026-07-08. Two consequences: - -- *Never treat a 100-row result as complete.* When a scan returns exactly 100, walk the tail in *date slices*: re-query with =before:<oldest-full-day-seen>= (day resolution), repeat until a page returns fewer than 100, dedupe by message id across slices (the day-resolution boundary overlaps). -- *Never report =resultSizeEstimate= as a count.* It's unreliable — observed stuck at "201" across three different queries whose real union exceeded 300. - -*** Backlog-residue check (every sweep — cheap, mandatory) - -The anchored scan is blind to anything unread from *before* the anchor. After it, run one probe for pre-anchor residue: - -#+begin_src text -mcp__google-docs-personal__listMessages q="is:unread in:inbox before:<anchor-YYYY/MM/DD>" maxResults=5 -#+end_src - -If it returns any messages, surface one loud line in the sweep summary: "Backlog: unread predating the anchor exists (N+ shown; date-slice to inventory)" and offer a backlog sweep. Never fold the residue into a quiet sweep — an anchored "no changes" claim is only true for the window the scan saw. (Added 2026-07-08 after ~300 pre-anchor unread accumulated unseen; the probe returns actual messages, so it works where the estimate lies.) - -** Classify - -Bias: *trash-leaning* — personal Gmail is high noise volume. - -- *Noise-trash:* newsletters, Substacks, retail/SaaS marketing, social digests, redundant aggregator digests (Notion/Miro daily), wrong-recipient mail, past-event calendar artifacts. -- *Noise-keep:* receipts, order confirmations, statements — low value but worth the audit trail. -- *FYI:* substantive personal mail with no action owed. -- *Action:* an explicit ask, a reply owed, a time-sensitive personal matter. - -** Render - -#+begin_example -**Personal Gmail — N unread.** <one-line classification summary> -- Action: <items, if any, with thread links> -- FYI: <items, if any> -- Noise: N trash candidates, M keep -#+end_example - -Omit the block if zero unread. - -** Actions - -- trash :: =mcp__google-docs-personal__trashMessage= id=<message-id> (recoverable from Gmail Trash for 30 days) -- mark-read :: =mcp__google-docs-personal__modifyMessageLabels= id=<message-id> removeLabelIds=["UNREAD"] -- star+read :: =mcp__google-docs-personal__modifyMessageLabels= id=<message-id> addLabelIds=["STARRED"] removeLabelIds=["UNREAD"] -- attach-fetch:: =.ai/scripts/gmail-fetch-attachments.py --profile personal --message-id <message-id> --output-dir <PATH>= diff --git a/inbox/PROCESSED-2026-07-09-0649-from-work-pr-review-rule-tightening-from-a.org b/inbox/PROCESSED-2026-07-09-0649-from-work-pr-review-rule-tightening-from-a.org deleted file mode 100644 index 80dc4bc..0000000 --- a/inbox/PROCESSED-2026-07-09-0649-from-work-pr-review-rule-tightening-from-a.org +++ /dev/null @@ -1,11 +0,0 @@ -#+TITLE: PR-review rule tightening from a DeepSat review session (Cra -#+SOURCE: from work -#+DATE: 2026-07-09 06:49:14 -0500 - -PR-review rule tightening from a DeepSat review session (Craig, 2026-07-09). Two changes to the review-code skill: - -1. No praise on approvals — stronger than the current 'Posted Summary Voice' rule. That section currently permits 'the verdict plus at most a bare positive ("Clean.", "Solid fix.")'. Craig's ruling: an approve summary carries NO praise at all, not even the bare positive. Lead the summary with the substantive pointer (the inline design note), then the verdict. Example he approved: 'One design note inline, not a blocker. Approving.' The praise-strips / correction-explains split still holds for findings; approvals just drop the praise clause entirely. Suggest editing the 'Posted Summary Voice' section (and /voice personal pattern #40 if it encodes the 'bare positive allowed' carve-out) to remove the bare-positive permission. - -2. Always show inline comment text at the review gate — Phase 5 / the publish-flow gate should require printing the FULL inline prose that will post, alongside the summary body, never the summary alone with the inline merely described ('I'd pair it with one inline on...'). Craig approves the exact words that post under his name, so the exact words must be on screen. Suggest making this explicit in review-code Phase 5 (Terminal display) and in commits.md Step 2 Shape 1 (the print-the-draft step). - -Both are cross-project (any PR review), so they belong in the rulesets layer, not just the DeepSat project. Also captured in the work project's harness memory as feedback_no_praise_on_approvals_show_inline for immediate use. diff --git a/inbox/PROCESSED-2026-07-09-1341-from-work-bug-data-loss-wrap-org-table-el-and.org b/inbox/PROCESSED-2026-07-09-1341-from-work-bug-data-loss-wrap-org-table-el-and.org deleted file mode 100644 index a128d0a..0000000 --- a/inbox/PROCESSED-2026-07-09-1341-from-work-bug-data-loss-wrap-org-table-el-and.org +++ /dev/null @@ -1,28 +0,0 @@ -#+TITLE: BUG (data loss): wrap-org-table.el and lint-org.el corrupt o -#+SOURCE: from work -#+DATE: 2026-07-09 13:41:56 -0500 - -BUG (data loss): wrap-org-table.el and lint-org.el corrupt org example blocks. - -Both scripts scan for lines beginning with "|" and rewrite them as org tables. They do not skip #+begin_example / #+begin_src / #+begin_quote regions, so ASCII art using pipe characters gets mangled into tables. Both write to disk with no confirmation. - -Reproduced 2026-07-09 in the work project against an architecture doc containing an ASCII pipeline diagram that uses | and v as flow arrows: - - Before: After: - | | | - v |---| - v - -and a plain indented block became a bordered org table with |---| rules inserted between every line. - -Two separable defects: - -1. Table detection is line-based. Both helpers should use org-element-at-point (or org-in-block-p) to skip example/src/quote/verse blocks rather than matching /^\s*|/. - -2. lint-org.el mutates its input. Passing five files to it reformatted all five on disk -- one of them by 1949 lines. Its documented job is to report judgment items. A linter must not write. If the reformat is wanted, it belongs behind an explicit --fix flag. - -Impact: silent data loss on any org file that mixes tables and example blocks, which is most architecture docs. In this case the good content was already staged in git and was recoverable. It would not have been otherwise. - -No local fix attempted: .ai/scripts/ is rulesets-owned and the startup rsync would revert it. Filed as a task on the work side (Org-table helpers corrupt example blocks) so it is tracked there until the canonical fix lands. - -Suggested test: run wrap-org-table.el against a file containing a #+begin_example block whose lines start with "|" and assert the block is byte-identical afterward. diff --git a/inbox/PROCESSED-2026-07-09-1400-from-work-handoff-ai-attribution-cleanup-done.org b/inbox/PROCESSED-2026-07-09-1400-from-work-handoff-ai-attribution-cleanup-done.org deleted file mode 100644 index a37a54a..0000000 --- a/inbox/PROCESSED-2026-07-09-1400-from-work-handoff-ai-attribution-cleanup-done.org +++ /dev/null @@ -1,22 +0,0 @@ -#+TITLE: HANDOFF: AI-attribution cleanup done from the work session ( -#+SOURCE: from work -#+DATE: 2026-07-09 14:00:05 -0500 - -HANDOFF: AI-attribution cleanup done from the work session (Craig approved doing it from here). - -What changed in rulesets, uncommitted in your working tree: - -1. 103 files: rewrote the org header "#+AUTHOR: Craig Jennings & Claude" to "#+AUTHOR: Craig Jennings". Breakdown: 43 .ai/workflows, 43 claude-templates/.ai/workflows, 5 docs/specs, 5 docs/design, 2 .ai (notes, protocols), 2 claude-templates/.ai, 2 references, 1 working/. Exactly one line changed per file (103 insertions, 103 deletions, zero non-AUTHOR lines). Prose mentions of Claude were not touched. - -2. claude-rules/commits.md: added "Document author metadata" to the No-AI-Attribution list, plus a new subsection "Generated documents carry the human author only". It explains that the propagation mechanism is imitation (no template stamps the line; agents copy it from neighbouring files), names the employer-policy stakes, and carves out two exceptions. - -Held back deliberately, please confirm you agree: -- .ai/sessions/ (14 files) left as-is. They are historical records of what happened, not live artifacts. -- docs/design/2026-05-28-generic-agent-runtime-spec.org and its -review sibling keep "#+AUTHOR: Codex". Codex actually wrote them, so renaming would be a false attribution rather than removing one. -- .ai/scripts/tests/fixtures/todo-sample.org keeps "#+AUTHOR: synthetic fixture" (test data). - -Not committed. The tracked tree was clean at 0/0 against origin/main before these edits, so the diff is exactly this change and nothing else. Review and commit on your side. - -Why it came up: the work project noticed its generated daily-prep docs carry the co-author line. Craig pointed out that his own repo tolerates it, but employers whose policy is that work product carries employee names alone would not. Nothing has leaked yet: the arch docs pushed to the company GHE lost the #+AUTHOR line in the pandoc conversion. The exposure was prospective, via a planned Markdown-to-Notion publisher. - -Companion item already in your inbox: the wrap-org-table.el / lint-org.el data-loss bug (2026-07-09-1341). diff --git a/inbox/PROCESSED-2026-07-09-1636-from-chime-staleness-proposal.txt b/inbox/PROCESSED-2026-07-09-1636-from-chime-staleness-proposal.txt deleted file mode 100644 index cc741b2..0000000 --- a/inbox/PROCESSED-2026-07-09-1636-from-chime-staleness-proposal.txt +++ /dev/null @@ -1,17 +0,0 @@ -Proposal: task-review-staleness.sh should accept org-style :LAST_REVIEWED: values, or fail loudly. - -Hit this in chime today. I stamped :LAST_REVIEWED: [2026-07-09 Thu] — an org inactive timestamp, matching the CREATED: and CLOSED: cookies sitting right next to it in the same drawer. The script expects a bare 2026-07-09. - -The failure is silent and inverted. In count mode, `date -d "[2026-07-09 Thu]"` fails, and the unparseable branch counts the task as STALE. So a freshly-reviewed task reports as never-reviewed, and a full review pass leaves the startup nudge saying exactly what it said before. In list mode the sort-key regex also rejects it, so the task sorts as 0000-00-00 (oldest) and gets re-walked first. Both modes punish the stamp for being in the wrong format, and neither says so. - -I fixed my side (bare dates, matching the precedent in home/todo.org). The trap is worth closing, because the bracketed form is the plausible guess: every other date in an org PROPERTIES drawer is bracketed, and nothing in task-review.org or todo-format.md says LAST_REVIEWED is different. - -Two options, either fine: - -1. Accept both. Strip a leading bracket and a trailing weekday + bracket before parsing, inside extract_tasks. Org-native stamps then work and existing bare stamps keep working. - -2. Fail loudly. When a LAST_REVIEWED value is present but unparseable, print a warning naming the file, line, and value rather than folding it into the stale count. A malformed stamp is a data error, and treating it as "never reviewed" hides it forever. - -I lean toward both: accept the org form, warn on anything still unparseable. Today a project can run task reviews for months while the staleness count never drops, and nothing ever explains why. - -Also worth a line in todo-format.md or task-review.org stating the expected format. The script is currently the only place it's written down, and you have to read its awk to find it. diff --git a/inbox/PROCESSED-2026-07-09-1745-from-chime-matrix-proposal.txt b/inbox/PROCESSED-2026-07-09-1745-from-chime-matrix-proposal.txt deleted file mode 100644 index 53c20c8..0000000 --- a/inbox/PROCESSED-2026-07-09-1745-from-chime-matrix-proposal.txt +++ /dev/null @@ -1,35 +0,0 @@ -Proposal: todo-format.md's bug matrix should warn against double-counting rarity. - -Adding the severity x frequency matrix to chime today, I mis-graded a bug by exactly one mistake, and I think the rule invites it. - -The task: chime's async watchdog interrupts a child that outlives its timeout, but never escalates to kill. I graded it Minor severity ("a zombie child and a leaked process buffer accumulate slowly") x rare edge case ("the watchdog must fire AND the child must survive SIGINT") = P4 = [#D]. - -Then I read async.el. Its cleanup guards on (eq 'exit (process-status proc)) and only kills the process buffer in the zero-exit branch, so a signal-killed child (status 'signal) skips it entirely. Every watchdog interrupt leaks a buffer; the surviving-SIGINT zombie is the rare sub-case, not the leak. And the watchdog nils the process handle, so the same tick spawns a replacement — if the hang cause persists, another child is abandoned every timeout period. Roughly 30 leaked buffers an hour, indefinitely, invisibly. A real incident had a child stuck 15+ hours. - -Severity was the wrong input, not frequency. "Accumulates slowly" describes a bounded trickle. This accumulates at a fixed rate forever once entered, with no workaround short of restarting Emacs. That's Major. Major x rare edge = P3 = [#C], which is where it landed. - -The generalizable error: I let the rarity of *entering* the failure state discount the *severity* of being in it. But frequency already carries that rarity. Grading it twice buries exactly the bugs that compound — the ones where a rare trigger produces unbounded harm. - -Suggested addition to the matrix section: - - Don't double-count rarity. Grade severity by the rate of harm once the - failure state is entered, not by how rare it is to enter. Frequency - already carries the rarity; letting it discount severity too grades the - same fact twice, and that buries compounding bugs. A leak that repeats - every timeout period until the process restarts is Major even when - reaching that state is a rare edge case. - -Two smaller additions I made to chime's scheme, both of which I'd put in the global rule: - - Record the grading in the task body — the severity band, the frequency - row, and the arithmetic. A bare priority cookie can't be argued with; a - stated read can be re-checked against the source and corrected. That's - how this task moved [#D] -> [#C] an hour after I graded it. - - Disagreeing with a grade means fixing an input. If a letter looks wrong, - re-read the severity band and the frequency row against the source and - correct whichever is wrong. Don't override the letter directly — that - turns the matrix into a formality and puts you back to grading by - instinct. - -The last one is the one I care about. Craig's first instinct on seeing the [#D] was to restore the [#B] it had before. The matrix earns its keep only if a disagreement forces a re-read of the inputs rather than a manual override, and the rule text currently doesn't say so. diff --git a/inbox/PROCESSED-2026-07-11-0222-from-.emacs.d-ui-prototype-rule-proposal.org b/inbox/PROCESSED-2026-07-11-0222-from-.emacs.d-ui-prototype-rule-proposal.org deleted file mode 100644 index eeb60e7..0000000 --- a/inbox/PROCESSED-2026-07-11-0222-from-.emacs.d-ui-prototype-rule-proposal.org +++ /dev/null @@ -1,55 +0,0 @@ -#+TITLE: Proposal: UI features require a prototype phase before build-to-spec -#+AUTHOR: Craig Jennings -#+DATE: 2026-07-11 - -* The rule (Craig approved promotion 2026-07-11) - -When a spec'd feature has a UI, don't build straight from the spec. After the -initial spec, run several UI/UX prototype feedback loops — iteratively driving -the remaining functionality alongside the look and feel — then fold what settled -back into the spec. Only then "build to the prototype": the built feature should -look and behave as close to the prototype as possible, and any deviation is -documented in an addendum section of the prototype/spec itself. - -* Where it should live (rulesets session decides exact home) - -Two natural homes; probably both: - -1. The =brainstorm= skill's Phase 3. Today Phase 3 presents the design in chunks - and stops. Add: if the feature has a UI, the design isn't "accepted" until it - has been through a prototype UI/UX phase (several feedback loops), and the - spec records what the prototype settled. The spec's Next Steps then say - "build to the prototype," not "build to the spec." - -2. A spec-lifecycle rule (=docs-lifecycle.md=, or a small new workflow rule). - The lifecycle for a UI feature gains a prototype stage between DRAFT/READY and - build, and the spec carries a "Prototype & deviations" addendum section that - the build keeps current. - -Companion touch points to reconcile: =spec-create= (emit the prototype stage + -the deviations-addendum section for UI specs), =spec-response= (a UI spec -decomposes into a prototype loop first, then build-to-prototype tasks), -=start-work= (its verify phase already drives the UI end-to-end; here the bar is -"matches the prototype," with deviations logged). - -* Why — worked example (takuzu, 2026-07-11) - -Building the takuzu (Binairo) Emacs game. The spec chose "colored tiles, glyph -overlay optional." Built straight to that and the first launch in Craig's actual -terminal frame was all black — the dark background-color faces read as black and -the cursor was a GUI-only =:box=, so the whole grid was invisible. The -colored-tiles-are-readable assumption was false in the real environment. A -prototype loop caught it on the first screenshot; had we "built to spec" and -called it done, we'd have shipped an unusable board. The fix (glyphs as the -primary signal, inverse-video cursor) is exactly the kind of adjustment that only -surfaces by looking at the running UI, and it now needs to flow back into the -spec so the build target is the prototype, not the original spec text. - -Jotto (the other game spec'd the same day) also has a UI and will follow the same -path. - -* Requested action - -Fold the rule into the brainstorm skill and the spec-lifecycle rules so it -governs every project's UI features, then re-sync. This proposal is the durable -channel; the two game projects apply it locally in the meantime. diff --git a/inbox/lint-followups.org b/inbox/lint-followups.org new file mode 100644 index 0000000..9d2bd8f --- /dev/null +++ b/inbox/lint-followups.org @@ -0,0 +1,18 @@ +* 2026-07-20 Mon — Task-review health: 1 top-level [#A]/[#B]/[#C] tasks unreviewed for >30 days (daily review may have slipped) + +* lint-org follow-ups — todo.org (2026-07-29) +** TODO misplaced-heading — Possibly misplaced heading line (line 2263) +** TODO link-to-local-file — Link to non-existent local file "working/hook-fail-open/validate-el.diff" (line 2239) +** TODO misplaced-planning-info — Misplaced planning info line (line 2228) +** TODO link-to-local-file — Link to non-existent local file "working/hook-fail-open/pre-commit.diff" (line 2223) +** TODO misplaced-planning-info — Misplaced planning info line (line 2208) +** TODO org-table-standard — table violates the org-table standard: no closing rule; missing rule between rows — wrap-org-table.el reflows it (line 314) +** TODO task-missing-last-reviewed — task has no :LAST_REVIEWED: — stamp it at creation with today's date (a task you just wrote and graded is reviewed); otherwise it enters the next staleness batch as never-reviewed (line 472) +** TODO task-missing-last-reviewed — task has no :LAST_REVIEWED: — stamp it at creation with today's date (a task you just wrote and graded is reviewed); otherwise it enters the next staleness batch as never-reviewed (line 475) +** TODO task-missing-last-reviewed — task has no :LAST_REVIEWED: — stamp it at creation with today's date (a task you just wrote and graded is reviewed); otherwise it enters the next staleness batch as never-reviewed (line 482) +** TODO task-missing-last-reviewed — task has no :LAST_REVIEWED: — stamp it at creation with today's date (a task you just wrote and graded is reviewed); otherwise it enters the next staleness batch as never-reviewed (line 490) +** TODO task-missing-last-reviewed — task has no :LAST_REVIEWED: — stamp it at creation with today's date (a task you just wrote and graded is reviewed); otherwise it enters the next staleness batch as never-reviewed (line 493) +** TODO task-missing-last-reviewed — task has no :LAST_REVIEWED: — stamp it at creation with today's date (a task you just wrote and graded is reviewed); otherwise it enters the next staleness batch as never-reviewed (line 502) +** TODO task-missing-last-reviewed — task has no :LAST_REVIEWED: — stamp it at creation with today's date (a task you just wrote and graded is reviewed); otherwise it enters the next staleness batch as never-reviewed (line 600) +** TODO task-missing-last-reviewed — task has no :LAST_REVIEWED: — stamp it at creation with today's date (a task you just wrote and graded is reviewed); otherwise it enters the next staleness batch as never-reviewed (line 759) +** TODO task-missing-last-reviewed — task has no :LAST_REVIEWED: — stamp it at creation with today's date (a task you just wrote and graded is reviewed); otherwise it enters the next staleness batch as never-reviewed (line 768) |
