| Commit message (Collapse) | Author | Age | Files | Lines |
| |
|
|
|
|
| |
send_file ran filenames through slugify(), which flattens dots to hyphens. That corrupts the engine.plugin.org plugin-namespace convention: triage-intake.personal-gmail.org arrived as triage-intake-personal-gmail.org, which breaks the engine's triage-intake.*.org glob and the routing that depends on the first dot.
I added slugify_filename() for filename stems. It keeps dots, hyphens, underscores, and case, collapses only whitespace runs to hyphens, and truncates on a separator boundary. The prose --text path still uses slugify().
|
| |
|
|
| |
The .ai/ mirror lagged claude-templates/.ai/ for three workflows (task-audit, task-review, triage-intake) and two scripts (screenshot.py and its test) — earlier commits updated the canonical copies without resyncing the mirror in the same commit. The startup rsync caught it up; this commit tracks the result so the two stay identical.
|
| |
|
|
|
|
|
|
|
|
| |
The new task-review.org workflow is the daily habit that retires the old date-coverage scan. It surfaces the oldest-unreviewed top-level tasks, walks them one at a time, and records each outcome — keep, re-grade, kill, mark DOING, or edit — stamping :LAST_REVIEWED: as it goes. It's a pure Claude workflow, no elisp. open-tasks.org displays the list; this one changes it.
task-review-staleness.sh gains a --list mode that emits the N oldest-unreviewed tasks (line, review date, heading), oldest first, so the workflow walks a deterministic batch instead of eyeballing todo.org. Never-reviewed and unparseable-date tasks sort oldest. Seven new bats cases cover ordering, the count limit, exclusions, and output format; count mode is unchanged.
startup.org gains the matching nudge. Phase A counts tasks unreviewed for >7 days and Phase C surfaces one line when that count is non-zero, pointing at the workflow. It lives in the template startup.org rather than the project-only startup-extras layer, so every project picks it up the same way it picks up the wrap-up health check.
The INDEX entry is added with the "task review" triggers the rename freed up.
|
| |
|
|
|
|
|
|
| |
First component of the daily task-review habit from docs/design/task-review.org. The staleness count is the shared primitive both the wrap-up health check (threshold 30) and the startup reminder (threshold 7) call, so it lives in one tested script rather than being reimplemented in each workflow.
The script counts top-level todo.org tasks whose review has gone stale: depth-2 headings with a TODO/DOING/VERIFY keyword and an [#A]/[#B]/[#C] cookie, where LAST_REVIEWED is missing, unparseable, or older than the threshold. Age uses a strict greater-than, so a task reviewed exactly N days ago is still fresh. Today normalizes to local midnight before the diff, and the day count rounds to the nearest day, so a DST hour can't push a boundary task across the line.
Twelve bats cases cover the normal, boundary, and error categories. Dates are generated relative to the current date rather than hardcoded. The script path resolves as the sibling-of-parent of the test file, so the suite runs identically from the canonical claude-templates tree and the rsync'd project mirror. Makefile test target now globs .ai/scripts/tests for bats alongside scripts/tests.
|
| |
|
|
|
|
|
|
|
|
| |
Project .ai/ mirror catches up to two canonical updates already in claude-templates/:
- lint-org cj-comment block suppression (3fb4c80). The =#+begin_src cj: ...= annotation pattern triggered three lint categories (suspicious-language, empty-header-argument, wrong-header-argument) as false positives at todo.org:16 and todo.org:1291. lint-org.el now recognizes the opener and skips all three on those lines.
- LINT_ORG_FOLLOWUPS default flipped to =./inbox/lint-followups.org= (684891d). The previous hardcoded default routed every project's wrap-up findings into the work project's inbox.
Phase A startup rsync brought both into the project mirror this morning; bundled into one chore commit since neither delta is project-specific work.
|
| |
|
|
| |
The project mirror at .ai/scripts/ was missing the wrapper_type state machine and TestCjScanNestedFencesIgnored suite that landed in dc1661c. That commit only touched claude-templates/.ai/scripts/. Phase A's startup rsync brings the mirror back in line with the canonical.
|
| |
|
|
|
|
|
| |
- todo-cleanup.el: :no-sync: tag now inherits down the outline tree
- task-review.org: completion procedure scoped to top-level entries
- cj-scan.py + cj-remove-block.py: helpers for cj-comment block handling
- inbox-send.py: cross-project messaging via inbox directories
|
| |
|
|
|
|
|
| |
Byte-identical pull of .ai/scripts/lint-org.el,
.ai/scripts/tests/test-lint-org.el, and the new Step 3 lint section in
.ai/workflows/wrap-it-up.org. Upstream: claude-templates 138f35f (feat)
and 4eba98c (docs).
|
| |
|
|
|
|
|
|
| |
The first take walked the heading line with a plain `\[#\([A-Z]\)\]` regex, which matched any cookie-shaped substring anywhere in the line. Dated-log headings can carry that shape inside the title — e.g. "Reprioritized children =[#D]= → =[#B]= to match parent" quotes earlier and new priorities verbatim, and the script read =[#D]= as if it were the heading's own priority cookie.
`(nth 3 (org-heading-components))` only returns a priority when the cookie sits in canonical position (right after the stars or the optional TODO keyword), which is the only place org itself recognizes it. That's the right primitive here.
Surfaced via smoke-testing --check-child-priority against ~/projects/work/todo.org: 10 candidates dropped to 9 once the dated-log heading inside the Whisper parent stopped getting flagged. New ert test tc-sync-ignores-cookie-shaped-text-in-title covers the case directly.
|
| |
|
|
|
|
|
|
|
|
| |
When a parent task in todo.org gets reprioritized, its children frequently keep their original (lower) priority cookies, which then mismatches the parent's new importance. The new mode walks every heading with a priority cookie and bumps any direct child whose own cookie is lower (D ranks below A in org's default scheme). Down-only: parents are never bumped up to a child's priority. Priority-less parents and priority-less children are both left alone — sync does not invent priorities.
Children opt out by carrying the :no-sync: literal tag, useful for Follow-up:/Spike: sub-tasks that are deliberately deprioritized. The tag match is literal regex against the heading line rather than going through org-get-tags, because org's default tag character class excludes hyphens — :no-sync: would not be parsed as a real tag in batch mode without a custom org-tag-re.
org-map-entries visits headings in document order, so a multi-level chain [#A] → [#B] → [#D] collapses to the top priority in one pass: the middle bumps to [#A] before the walk reaches the leaf.
wrap-it-up.org Step 3 now invokes --sync-child-priority after --archive-done. --check-child-priority is the report-only alias (--sync-child-priority --check) for previewing before applying. Default cadence is auto-apply, same as --archive-done.
|
| |
|
|
|
|
|
|
| |
--archive-done moves every level-2 subtree whose TODO state is DONE or CANCELLED out of the "Open Work" section into the "Resolved" section of the same org file, subtree intact. Sections match on a unique level-1 heading containing "Open Work" (case-insensitive) and one containing "Resolved"; a missing or ambiguous section skips the file with a message rather than crashing. Only direct level-2 children move. A DONE entry nested under an open parent stays put. Opt-in, never run by default, doesn't also run the hygiene passes; --check previews without writing.
The CLI dispatch moved into tc-main behind a guard so the new ERT suite can require the file without firing it. Hygiene mode is unchanged.
13 ERT cases (the repo's first elisp tests) cover the move and the stay-put cases, EOF with no final newline, missing or ambiguous sections, lowercase headings, idempotency, and --check. tests/fixtures/todo-sample.org is the synthetic sample, and the Makefile test target now runs the ERT suites alongside pytest.
|
| |
|
|
|
|
|
|
| |
Add cmail-action.py for IMAP triage operations against Proton Mail
Bridge (list-unread, read, mark-read, star, unstar, trash, send,
folders) mirroring the Gmail MCP workflow. Also add comprehensive
tests for cmail-action, gmail-fetch-attachments, and
maildir-flag-manager scripts.
|
|
|
Replace the seed notes.org with project-specific context (layout, install modes, task tracker location, recent inflection point). Bring in the synced template surfaces (protocols, workflows, scripts, references, retrospectives, someday-maybe) as tracked content for this content/documentation project.
|