Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
23 commits
Select commit Hold shift + click to select a range
8eb3322
feat(core): module event type, kept out of task views
Shahinyanm Oct 4, 2026
f976bc4
feat(core): project modules, task links and module history from the j…
Shahinyanm Oct 4, 2026
0a934b6
feat(core): suggest modules for a task without a model
Shahinyanm Oct 4, 2026
d1b4b58
feat(core): module page and the pack's Modules line
Shahinyanm Oct 4, 2026
811b73d
feat(core): archive gaps — what the chronicle is missing and what to do
Shahinyanm Oct 4, 2026
3cb7ad5
feat(mcp): chronicle tools and module fields on create, close and search
Shahinyanm Oct 4, 2026
3096776
feat(cli): module commands, --modules, --module-note, chronicle line …
Shahinyanm Oct 4, 2026
aaee371
feat(mod): module in the status line, chronicle gaps that open mid-se…
Shahinyanm Oct 4, 2026
02f3b5c
docs(plugin): chronicle ritual in the skill and /task-journal:map
Shahinyanm Oct 4, 2026
0f0a1f0
chore: 0.31.0 — project chronicle
Shahinyanm Oct 4, 2026
970082e
fix(mod): refresh the status line after module_link and module_save
Shahinyanm Oct 4, 2026
702ab61
fix(core): module page keeps every section on real-sized entries
Shahinyanm Oct 4, 2026
43d1ae3
fix: chronicle gaps put actionable ones first; backfill pages with of…
Shahinyanm Oct 4, 2026
cee06ea
fix(cli): keep module lines out of the JSON export too
Shahinyanm Oct 4, 2026
cdf3a42
fix(mod): never bring up a chronicle gap the session has already seen
Shahinyanm Oct 4, 2026
0a8c2c8
fix: a git worktree is not asked to map the project again
Shahinyanm Oct 4, 2026
08028f8
fix(core): module suggestions — titles only back a match, whole-word …
Shahinyanm Oct 4, 2026
7eaac68
docs: correct the 0.31 upgrade notes; move a doc comment back to its …
Shahinyanm Oct 4, 2026
9745dbd
feat: one module map per repository — git worktrees share their main …
Shahinyanm Oct 4, 2026
c142c8c
fix(core): accept a worktree's chronicle home only when the repositor…
Shahinyanm Oct 4, 2026
e979785
fix(core): a symlinked .git cannot borrow another worktree's chronicle
Shahinyanm Oct 4, 2026
e0fe78f
fix(mcp): readable module reminder after closing a task
Shahinyanm Oct 4, 2026
49629e8
fix: the chronicle visits worktree journals one at a time and only in…
Shahinyanm Oct 4, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 2 additions & 2 deletions .claude-plugin/marketplace.json
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,14 @@
},
"metadata": {
"description": "Task Journal — append-only reasoning chain memory for AI-coding tasks",
"version": "0.30.0"
"version": "0.31.0"
},
"plugins": [
{
"name": "task-journal",
"source": "./plugin",
"description": "Append-only journal of AI-coding task reasoning chains. Captures hypotheses, decisions, rejections, evidence — renders compact resume packs so an agent can pick up a 2-week-old task with full context.",
"version": "0.30.0",
"version": "0.31.0",
"author": {
"name": "Digital-Threads"
},
Expand Down
59 changes: 59 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,65 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

## [Unreleased]

## [0.31.0] - 2026-10-04

The journal becomes a map of the system. A project splits into modules — parts
of the system by meaning, not folders or tickets — every task belongs to one or
more, and each module keeps its history. The agent keeps this chronicle up by
itself: the journal says what is missing and what to do about it.

### Added
- **Modules.** `module_save` creates or updates a module: name, description,
`hints` (code path prefixes and terms), `state` — a short living text of how
it works now — and status (`active`, `retired`, `merged`). Modules live in
the journal as a new `module` event, so a rebuild restores them.
- **Links.** `task_create(modules=[...])`, `module_link` for many tasks at once,
and `task_close(module_notes=[...])`: one line per module on what the task
changed there. Links ride in the `open` / `amend` / `close` events 0.30
already reads. An unknown module fails the call before anything is written;
a merged module links to the one that took it over.
- **Module page.** `module_page` (CLI `module show`): the module's state, the
active decisions, rejections and constraints of all its tasks, open tasks,
and history. A task's pack names its modules.
- **Suggestions without a model.** A new task without modules gets
`suggested_modules` from its words (English and Russian forms) and, for old
tasks, its files.
- **The chronicle keeps itself up.** The journal names what is missing — no
module map, tasks without a module, a module whose state lags behind its
tasks, an active task without a module — at session start (every client,
Codex included), in `task_create` / `task_close` / `module_list` replies, in
`task-journal state` (`archive`), and in the Claude Code mod when a gap opens
mid-session. The mod's status line shows the task's modules.
- **Mapping and sorting old work.** `/task-journal:map` and the skill's steps:
propose modules, confirm with the user, save them, sort past tasks with
`module_backfill_candidates` (paged with `limit` / `offset`), confirm, link —
leftovers to a catch-all module — and write each module's first state.
- **One map per repository, worktrees included.** A git worktree reads and
writes the module map of its main checkout, while its tasks stay in its own
journal. A module's page, task counts and staleness gather the tasks of the
main checkout and of every worktree, removed ones too. Worktrees register
next to the journals, and their module links carry the main checkout's id,
so the registry can be rebuilt from the journals.
- CLI: `module list|show|save|link|candidates`, `create --modules`,
`close --module-note module=text`; `task_search` / MCP gain a `module` filter.

### Changed
- `migrate-project` re-keys the module tables too.
- Task views (`events list`, every `export` format, backfill) skip `module`
lines, so hosts that group an export by task id see no phantom tasks. The
JSONL log itself remains the full record.

### Upgrading
- Restart open Claude Code and Codex sessions after `cargo install --force`.
The first command re-indexes the project once.
- A 0.30 binary next to 0.31 skips `module` lines with a warning and keeps all
tasks; 0.31 re-indexes once afterwards, so no module is lost.
- Existing tools, commands and packs work as before. What is new before you
create a module: the session start shows a `📚 Chronicle:` line inviting you
to map the project, `task_create` replies may carry
`chronicle` and `suggested_modules`, and `task-journal state` gains
`archive` and `active.modules`.

## [0.30.0] - 2026-10-04

Claude Code 2.1.287 added mods: plugins that run inside Claude Code and can
Expand Down
6 changes: 3 additions & 3 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 2 additions & 2 deletions Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ members = [
]

[workspace.package]
version = "0.30.0"
version = "0.31.0"
edition = "2021"
rust-version = "1.88"
license = "MIT"
Expand All @@ -20,7 +20,7 @@ categories = ["command-line-utilities", "development-tools"]
[workspace.dependencies]
# `version` must equal workspace.package.version: `cargo publish` uploads it as
# the requirement on core. Cargo can't inherit it; plugin_metadata.rs checks it.
tj-core = { package = "task-journal-core", version = "0.30.0", path = "crates/tj-core", default-features = false }
tj-core = { package = "task-journal-core", version = "0.31.0", path = "crates/tj-core", default-features = false }
anyhow = "1"
thiserror = "1"
serde = { version = "1", features = ["derive"] }
Expand Down
4 changes: 4 additions & 0 deletions INSTALL.md
Original file line number Diff line number Diff line change
Expand Up @@ -157,6 +157,10 @@ keeps writing next to the new one. The first command after the upgrade
re-indexes the project once (a few seconds for a large journal); later calls
are incremental.

0.31 adds `module` lines to the journal (the project chronicle). A 0.30 binary
still running next to it skips those lines with a warning and keeps every task;
the next 0.31 command notices and re-indexes once, so no module is lost.

## Verify

```bash
Expand Down
16 changes: 13 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -104,6 +104,7 @@ that tie it back to the code.
- **The mod (Claude Code 2.1.287+).** A plugin of function hooks that runs inside Claude Code and calls the `task-journal` CLI. It keeps the session's active task in the system prompt (a compaction can't drop it), gives each session its own active task, shows the task in the status line, reminds the agent to log only after several prompts without an entry, and — right before a compaction — asks the model what was never logged and records it as `suggested` events. It needs no setup. When it runs, the classic hooks skip what it replaces (the reminder, per-message classification and the transcript catch-ups) and keep the rest (resume packs, push-recall, `/rewind`). Codex and Claude Code older than 2.1.287 keep using the hooks below; there the mod simply doesn't load.
- **Self-tagging is the primary path (recommended).** You — the agent in the live session — record reasoning directly via the five MCP tools: open a task with a `goal`, append a typed `decision` / `finding` / `rejection` / `evidence` event at the moment of commitment, and `task_close` with a written `outcome`. This is free (it rides the interactive session), language-agnostic, and higher-fidelity than any after-the-fact classifier. The bundled `task-journal` skill drives this automatically. See [MCP tools](#mcp-tools).
- **Auto-capture is an opt-in backstop — OFF by default (v0.14.0).** A fresh `install-hooks` wires only a cheap, read-only SessionStart resume hook: no per-message classifier runs, no `claude -p` is ever spawned, nothing is charged. Self-tagging is the capture mechanism. Opt in with `install-hooks --auto-capture` and Claude Code hooks also run every prompt, tool call, and reply through a two-stage classifier that lands typed events on its own: Stage 1 is a fast in-process heuristic (obvious EN+RU phrasing, zero cost); Stage 2 falls back to an LLM only when the heuristic is uncertain (and only if you pick `--backend agent-sdk` / `api`). Even opted in it is a safety net under your explicit self-tagging, not the main mechanism, and it misses real reasoning — especially non-English prose.
- **Project chronicle (0.31).** The journal is also a map of the system: the project splits into **modules** — parts of the system by meaning, not folders or tickets — and every task belongs to one or more. Each module has a page: how it works now, the decisions, rejections and constraints of all its tasks, and its history, one line per task. A new task can start from that page; closing it adds its line. The journal suggests a module for a new task (from its words and files, no model call) and names what the chronicle is missing — no map yet, tasks without a module, a module whose state lags behind its tasks — at session start and in tool replies, so the agent keeps it up by itself. `/task-journal:map` (or the skill's steps in any client) maps a project and sorts its past tasks, with the user confirming both. A repository has one map: git worktrees share their main checkout's, and a module's history gathers tasks from every worktree, while each task stays in its own worktree's journal.
- **Artifact extraction.** Each event scans its text for commit hashes, PR URLs, file paths, issue IDs, and branch names. Aggregated artifacts are how Task Journal links related tasks: when you start a new task touching the same issue or file, the prior task is surfaced automatically.
- **Resume packs.** `task_pack` (MCP tool or CLI) renders a task into a compact Markdown briefing — Goal, Outcome, decisions, rejections, evidence, artifacts — that fits in a fresh agent's context window without dumping the raw event log.
- **Auto-capture boundaries.** Beyond per-event capture, two extra hooks mark *reasoning boundaries* automatically. On `PreCompact`, Task Journal reads the transcript JSONL tail (entries newer than the active task's last event) and enqueues anything the synchronous hooks missed before the compact — then drops a marker decision so the post-compact agent sees a clear cut. A `/rewind`-prefixed prompt appends a single correction event so pack readers see where the user rolled back. No mass-rejection of prior events — the boundary is a sentinel, not a rewrite.
Expand Down Expand Up @@ -169,13 +170,14 @@ task-journal pack tj-x9rz1f --mode full

| Command | What it does |
|---------|--------------|
| `create <title> [--goal "..."]` | Open a task with optional goal |
| `create <title> [--goal "..."] [--modules a,b]` | Open a task with optional goal and modules |
| `module list [--json] \| show <id> \| save <id> [--name] [--description] [--path P] [--term T] [--state] [--status] [--merged-into] \| link <task> [--add M] [--remove M] \| candidates [--limit N]` | The project chronicle: module map, module pages, creating and linking modules, tasks without a module |
| `goal <id> "..."` | Set or replace a task's goal |
| `event <id> --type X --text Y [--suggested] [--session S] [--origin O]` | Append a typed event |
| `state [--session S]` | The session's active task, counts and latest entries as JSON (what the mod reads) |
| `event-correct --corrects <eid> --task <id> --text "..."` | Correct an earlier event |
| `external <id> "..."` | Append an external reference (URL, ticket, linked task) |
| `close <id> --outcome "..." --outcome-tag done\|abandoned\|superseded` | Close with outcome |
| `close <id> --outcome "..." --outcome-tag done\|abandoned\|superseded [--module-note module=text]` | Close with outcome (and a line of each module's history) |
| `reopen <id> --reason "..."` | Reopen a closed task |
| `pack <id> --mode compact\|full` | Render a resume pack |
| `events list [--limit N]` | List recent events |
Expand All @@ -198,7 +200,7 @@ task-journal pack tj-x9rz1f --mode full

## MCP tools

The MCP server exposes seven tools to Claude Code, Codex and any MCP client:
The MCP server exposes these tools to Claude Code, Codex and any MCP client:

| Tool | Purpose |
|------|---------|
Expand All @@ -209,6 +211,14 @@ The MCP server exposes seven tools to Claude Code, Codex and any MCP client:
| `task_pack` | Render a resume pack |
| `task_search` | Search tasks: full text, or `status="open"` with no query to list them |
| `task_check` | Score a task's completeness and list its gaps |
| `module_list` | The module map and what the chronicle is missing |
| `module_page` | A module's page: state, decisions, rejections, constraints, history |
| `module_save` | Create or update a module (partial) |
| `module_link` | Link tasks to modules, many at once |
| `module_backfill_candidates` | Tasks without a module, with suggestions, for sorting old work |

`task_create` takes optional `modules` and suggests some when they're missing;
`task_close` takes optional `module_notes`; `task_search` takes an optional `module`.

The write tools take an optional `session_id`; Claude Code (through the mod) and
Codex (through each call's metadata) fill it in, so every session keeps its own
Expand Down
Loading
Loading