aboutsummaryrefslogtreecommitdiff
path: root/.ai/workflows/process-inbox.org
diff options
context:
space:
mode:
authorCraig Jennings <c@cjennings.net>2026-05-28 08:56:24 -0500
committerCraig Jennings <c@cjennings.net>2026-05-28 08:56:24 -0500
commit0c7eb59f813b5572cc32beb6d2dd09355639cbfc (patch)
tree188aa3f25b4e1a02c26fd79a17fa2d68ec5c26a1 /.ai/workflows/process-inbox.org
parent8dfbe5c4d148b9bced5ffd632521566cf9255aa0 (diff)
downloadrulesets-0c7eb59f813b5572cc32beb6d2dd09355639cbfc.tar.gz
rulesets-0c7eb59f813b5572cc32beb6d2dd09355639cbfc.zip
feat(workflows): add process-inbox.org with value-gate discipline
Generic process-inbox workflow at claude-templates/.ai/workflows/ and mirror. Owns inbox discipline across every project: items are ideas to evaluate, not orders to execute, and earn a place in todo.org or git history only when they pass a three-question value gate. The gate (Phase B): - Advances an existing TODO (look up by topic). - Improves how the project works (architecture, workflows, tooling, rule hygiene). - Serves the project's stated mission (read from notes.org Project-Specific Context). One yes accepts. Three nos reject. Per-source rejection flow (Phase D): - From Craig: state in chat, wait for override. - From another project: write a response via inbox-send naming which gate question failed plus any reconsideration condition. Silent rejection on a handoff is worse than no reply. - From a script or automated system: just delete. Phase B.1 gates filing on priority-scheme presence. If todo.org has a scheme at the top, file with cookie + mandatory type tag + optional effort/autonomy tags. If not, surface a one-sentence nudge to adopt one (or to skip grading and flag the gap in the commit). Phase D within accepts splits implement-now / fold-into-existing / file-as-TODO so the inbox doesn't default to inflating todo.org for every item that passes the gate. Phase E stamps :LAST_INBOX_PROCESS: in notes.org Workflow State if the section exists. startup.org Phase C step 2 now delegates here instead of inlining the inbox-processing language. INDEX entry under Tasks and planning lists the full set of trigger phrases.
Diffstat (limited to '.ai/workflows/process-inbox.org')
-rw-r--r--.ai/workflows/process-inbox.org172
1 files changed, 172 insertions, 0 deletions
diff --git a/.ai/workflows/process-inbox.org b/.ai/workflows/process-inbox.org
new file mode 100644
index 0000000..c6b3f79
--- /dev/null
+++ b/.ai/workflows/process-inbox.org
@@ -0,0 +1,172 @@
+#+TITLE: Process Inbox Workflow
+#+AUTHOR: Craig Jennings & Claude
+#+DATE: 2026-05-28
+
+* Overview
+
+Inbox items are *ideas to evaluate*, not orders to execute. They arrive from Craig (typed directives saved as files), from other projects (handoffs via =inbox-send=), and from scripts/automated systems. Each is a proposal. An item earns a place in =todo.org= or git history only when it passes the value gate: it advances an existing task, improves how the project works, or serves the project's stated mission.
+
+The workflow is the disposition discipline. Read each item, evaluate honestly, apply the decision, then notify the sender if it was a project handoff and you're rejecting. Silent rejection on a handoff is worse than no reply.
+
+* When to Use This Workflow
+
+User triggers:
+
+- "process inbox" / "process the inbox"
+- "handle the inbox"
+- "what's in inbox" / "what's in the inbox"
+- "let's clear the inbox" / "let's process the inbox items"
+
+Auto-invocation:
+
+- Startup =Phase C step 2= delegates here when the inbox is non-empty. Don't ask Craig — just run it.
+
+Do *not* invoke this for inbox items that are clearly out-of-scope for the project — those are cross-project routing problems, handled per the cross-project boundary rule in =protocols.org=.
+
+* The Value Gate
+
+Every inbox item passes through three questions. One *yes* is enough to accept.
+
+1. *Does it advance an existing TODO?* Look up by topic in =todo.org='s open work. If the item extends a filed task, fold it in. If it implements a filed task, do the work.
+2. *Does it improve how the project works?* Architecture cleanup, workflow refinement, tooling, rule hygiene, drift detection — anything that makes the project itself more effective.
+3. *Does it serve the project's stated mission?* Read =notes.org= *Project-Specific Context* if the mission isn't obvious from the working directory and current task. The item should advance that mission, not orbit it.
+
+Three *no*s means reject. The rejection isn't lazy — an idea that doesn't help any current task, doesn't improve the system, and doesn't serve the mission is genuine noise, and accepting it inflates =todo.org= without payoff.
+
+* Phase A — Inventory (one parallel batch)
+
+Issue these reads in one parallel batch:
+
+1. List =inbox/= excluding =.gitkeep= and =PROCESSED-*= prefixes (use =\ls -la inbox/= per the protocols.org exa-alias note).
+2. Read =notes.org= *Project-Specific Context* if mission isn't already loaded in the session.
+3. Read =todo.org='s top-of-file priority scheme if present (look for a =* Priority and Tag Scheme= section or similar between the intro and the first =* <Project> Open Work= header).
+
+For each inbox file, parse the filename for sender. Two common patterns:
+
+- =YYYY-MM-DD-HHMM-from-<sender>-<topic>.<ext>= — from another project via =inbox-send=.
+- =<topic>.org= — typically from Craig directly, or from a script.
+
+Note the file type. =.eml= files need the extract script (not raw =Read=):
+
+#+begin_src bash
+# View mode
+python3 .ai/scripts/eml-view-and-extract-attachments.py inbox/<file>.eml
+
+# Pipeline mode (extract attachments to a directory)
+python3 .ai/scripts/eml-view-and-extract-attachments.py inbox/<file>.eml --output-dir assets/<target>/
+#+end_src
+
+Everything else, read directly.
+
+* Phase B — Evaluate each item
+
+For each inbox file:
+
+1. *Read it.* For substantive proposals (org files with TODO entries, design notes, multi-section docs), the full read is the right move. For short FYIs and one-liner asks, skim.
+2. *Identify the shape.* Is it an instruction, a question, a proposal, an FYI, or a handoff? Shapes guide disposition.
+3. *Apply the value gate.* Three questions above. One yes → candidate accept. Three nos → candidate reject.
+4. *Within accept, classify:*
+ - *Implement now* — small, scoped, clear, no design call required. The work is the disposition.
+ - *Fold into existing TODO* — the item extends a task already filed; update the TODO body and link the inbox content if substantive.
+ - *File as TODO* — substantive but waits, or needs design/triage before implementation.
+5. *Within reject, classify by source:*
+ - *From Craig* — push back honestly in chat. State why you won't implement. Offer the conditions under which you would, if any. Wait for Craig to override or accept.
+ - *From another project* — write a response file naming the rejection rationale and (optionally) the condition under which you'd reconsider. Deliver via =inbox-send <sender> --file <response>= per the cross-project handoff convention.
+ - *From a script or automated system* — just delete; no notification needed.
+
+* Phase B.1 — Priority-scheme check
+
+This gates Phase C filing when there are accept-and-file items.
+
+Check whether =todo.org= has a top-of-file priority scheme (an explicit legend defining =[#A]= through =[#D]= semantics and mandatory/optional tag conventions).
+
+- *Scheme present* — file new TODOs per the scheme. Every TODO gets a priority cookie matching the legend's rules, the mandatory type tag, and any applicable effort/autonomy tags.
+- *Scheme absent* — surface one sentence: "This project has no priority scheme. We should adopt one before filing the new TODOs from this inbox pass — want me to propose one based on the rulesets scheme?" If Craig says yes, do that first (the =/research-priority-scheme= research subagent pattern in rulesets is the reference). If Craig says no, file the TODOs without grading but flag in the commit message that they're un-prioritized pending a scheme.
+
+The point is to avoid adding ungraded =TODO= entries to a project that's never agreed on what =[#A]= means.
+
+* Phase C — Surface dispositions
+
+Numbered options inline per =interaction.md= (no popup). Recommendation at item 1.
+
+Batch trivial items (one-line rejections of script noise, obvious file-as-TODO accepts where the scheme is already settled) into a single confirm-all prompt. Walk substantive items one at a time so the decision is visible.
+
+Per-item template:
+
+#+begin_example
+<filename> from <sender>: <one-line summary>
+Value-gate read: <yes/no on each of the three questions, one phrase each>
+Disposition recommendation: <implement / fold into <TODO> / file [#X] :tags: / reject>
+
+1. <recommendation as item 1>
+2. <alternative>
+3. Defer — leave in inbox under PROCESSED-<topic>.<ext> until <condition>
+4. Something else
+#+end_example
+
+For pure FYIs that need no action, surface as a single line and recommend delete-with-acknowledgment.
+
+* Phase D — Apply
+
+Apply each disposition. The flow is autonomous past Craig's Phase C approval.
+
+** Implement-now
+
+Do the work. Commit per the project's commit flow. Delete the inbox file. The commit message references the inbox item by filename so the provenance lands in =git log=.
+
+** Fold into existing TODO
+
+Update the parent TODO's body with a dated reconciliation sub-entry per =todo-format.md= (=*** YYYY-MM-DD Day @ HH:MM:SS -ZZZZ <what landed>=). Move substantive content to =docs/design/<date>-<topic>.<ext>= if it's worth keeping; reference from the TODO body. Delete the inbox file.
+
+** File as TODO
+
+Add the TODO under =* <Project> Open Work= with priority + tags per Phase B.1. Body summarizes the proposal and links the inbox content if it's been moved to =docs/design/=. Delete the inbox file (or move it to =docs/design/= first if the content survives).
+
+** Reject from Craig
+
+State the rejection in chat clearly: what you won't implement, why, and the conditions (if any) under which you would. Wait for Craig's override or acknowledgment. The inbox file stays until Craig confirms — if he overrides, re-enter Phase D as accept; if he acknowledges the rejection, delete the file.
+
+** Reject from another project (handoff)
+
+Write the response file at =/tmp/inbox-response-<topic>.org=. Contents:
+
+- Heading naming the original handoff and date
+- One paragraph: the rejection rationale (which value-gate question failed and why)
+- One paragraph: the condition under which you'd reconsider, if such a condition exists. If the answer is "never, this misreads the project's mission," say so directly.
+
+Deliver via =inbox-send <sender> --file /tmp/inbox-response-<topic>.org=. The =inbox-send= script (per =cross-project.md=) handles the from-prefix, date stamp, and target inbox path.
+
+Delete the local inbox file after the response lands in the sender's inbox.
+
+** Reject from script or automated system
+
+Just delete. No notification.
+
+** Defer
+
+Rename in place to =inbox/PROCESSED-<original-filename>= and add a brief comment line at the top: =# Deferred YYYY-MM-DD: <condition>=. Don't accumulate deferred items indefinitely — sweep them on a future =process-inbox= run when the condition is met or the deferral has aged out.
+
+* Phase E — Close out
+
+Verify =inbox/= is empty (excluding =.gitkeep= and any intentional =PROCESSED-*= files). Run =\ls -la inbox/= and confirm.
+
+Update the session log per =protocols.org= with one short paragraph summarizing this pass: count processed, count accepted (implement/fold/file split), count rejected (Craig/handoff/script split), and the commit SHA if a commit landed.
+
+Stamp =:LAST_INBOX_PROCESS:= in =notes.org='s *Workflow State* section if it exists, so future workflows that gate on freshness can read it. Same format as =:LAST_AUDIT:= (=YYYY-MM-DD=).
+
+* Common Mistakes
+
+1. *Treating items as orders.* Inbox content is a proposal. The value gate is the rule. Implementing every item without evaluation inflates =todo.org= and trains senders to keep sending noise.
+2. *Filing without applying the value gate.* "File as TODO" is not a default — it's the disposition for proposals that pass the gate but wait. A reject is also a valid file-as-TODO answer to nothing.
+3. *Filing raw TODOs when the project has a priority scheme.* Phase B.1 is mandatory when the scheme exists. An un-graded TODO in a project with a legend is a defect.
+4. *Silently deleting a project handoff.* Send a response. The sender's next session sees the response in their inbox and learns the rejection rationale. Silent rejection trains the sender to escalate to Craig instead of through the inbox channel.
+5. *Pushing back on a Craig directive only to immediately implement it anyway.* If you genuinely think Craig is wrong, say so and wait for his call. If you don't, just do the work — don't theatre the pushback.
+6. *Skipping the implement-vs-fold-vs-file classification.* Defaulting every accept to "file as TODO" turns the inbox into a queue that flows into =todo.org= without filtering. Small, scoped, clear items get implemented now; substantive proposals get filed; extensions to existing work get folded.
+7. *Not propagating value-gate failure to the response.* When you reject a handoff, the response should name *which* gate question failed (advances no current task / doesn't improve the project / doesn't serve the mission) so the sender can recalibrate, not just resend.
+8. *Forgetting to delete the inbox file after acting.* The inbox should be empty when this workflow ends. Files left behind become noise on the next startup.
+
+* Living Document
+
+Refine the value gate's three questions if the project's mission sharpens. Tune the per-source rejection-response template if =inbox-send= response loops surface a pattern. Add new auto-classification shortcuts if certain item shapes (e.g. routine FYIs from a script) become common.
+
+The workflow is shaped by use. The principle that inbox items are *ideas to evaluate* is the part that doesn't change.