Skip to content

Changelog

Also available as an Atom feed.

All notable changes to this project are recorded here. The format follows Keep a Changelog, and versions follow Semantic Versioning.

  • Simplicity is a tested budget (crates/sprig-cli/tests/budget.rs): the number of marks, commands, flags, fields with a meaning, diagnostic codes and MCP tools is pinned, and the card and the core of the spec have a ceiling. Adding one fails until the number is raised in the same pull request.

  • The whole format on one card, at the top of the spec and in the README, held to §2.2’s marks and §4.6’s fields. The RFC template asks what a proposal adds to it.

  • The spec is a core and an annex: the rules a reader needs in spec/sprig.md, and the rulings on edge cases, under their own numbers, with the grammar and the tree format, in spec/annex.md. The site shows both on one page.

  • CONTRIBUTING.md starts with a first change that needs only Rust, and the home page starts with a plan and what Sprig says about it.

  • The playground shows what sprig check would say as you type: each problem with its code, linked to its note, and what to do about it. Choosing one goes to its line, a line with a problem is marked in the editor, and a file’s tab carries a dot.

  • The playground on a phone: Source, Plan and Problems one at a time, each as tall as what it holds, so only the page scrolls; long lines wrap; a key bar stands in for Tab, Shift-Tab and the mark shortcut; Share opens the phone’s share sheet.

  • Files in the playground can be renamed, which carries every link to them, downloaded and deleted.

  • Every control on the site is at least 44px by touch, and long terminal and code lines fade at the edge they scroll towards. The site build checks every page at a phone’s and a tablet’s width, and drives the playground wide and narrow.

  • ARCHITECTURE.md, a map of the code for a newcomer: what each crate and top level folder does, how a file becomes an answer, and the invariants a change must keep, each with where it is enforced.

  • A README for every crate and for spec/, docs/, editors/, examples/, scripts/ and design/, and SUPPORT.md, saying where to ask what. The crates’ Cargo metadata names their README, keywords and categories, and the examples in the core’s and the tree-sitter grammar’s READMEs run as tests.

  • A test that every path a document names, as a Markdown link or in backticks, exists. It found a module citing a spec file that was never written; refs are specified in T1 of spec/tools.md.

  • scripts/task lint refuses a committed package, archive or file over 1 MiB.

  • scripts/task audit checks every lockfile against the RustSec and npm advisory databases. CI runs it weekly and on dependency changes, and Dependabot now watches every lockfile, which a test holds it to.

  • The conformance suite holds 417 examples, with every numbered rule of the spec cited:

    • Dates, shortcuts and estimates are checked against an oracle written from the spec, not from the parser.
    • Edit examples hold ticking (§10.4) and formatting (§3.3, §9.4) to exact bytes.
    • A coverage report in tests/conformance/README.md lists each rule’s examples, and CI fails when a rule has none.
  • docs/stability.md, the stability policy. Every promise names the test that keeps it, and a test fails if that test disappears.

  • --plain snapshots for next, check, tree, status, find and agenda.

  • rfcs/, the process for changing the spec, with its template. The rulings on times of day, email addresses and file versions are RFCs 0001 to 0003. CONTRIBUTING says who decides and how long review stays open.

  • Fuzz targets for the parser and the edit API (scripts/task fuzz), seeded from the suite, and a minute of each in CI.

  • The site’s reference gains the MCP tools and the diagnostics, generated from the server and the catalogue. CI fails on a command, option or diagnostic without documentation.

  • The tutorial ends with ticking the plan and handing it to an agent.

  • The command answers questions, and the editor writes (cairn 0154): 22 commands became 13. A removed command exits 2 and names its replacement.

    • status is tree --summary, and status --oneline is tree --summary --oneline.
    • agenda is find is:open 'due:<=+2w'; the TUI keeps the agenda view.
    • mark REF MARK is tick REF --mark MARK.
    • answer, add and edit are a line typed in an editor. The MCP server’s answer_question, add_items and mark_item stay, for agents.
    • graph is export --format dot or --format mermaid.
    • agent is mcp --instructions, and agent --write is mcp --instructions --write.
    • completions SHELL and man are generate SHELL and generate man.
  • tick reports what a change unblocked, on standard error, so its standard output stays a line per ref.

  • sprig-core’s public API, reviewed for 1.0:

    • Every public item is documented, and every public function has an example that runs as a test.
    • These are now #[non_exhaustive], so a later version can add to them: Code, Wait, Piece, query::Is, QueryError, RefError and EditError.
    • These are no longer public, as nothing outside the crate used them: syntax::estimate_hours, date::recurs, Date::add_month and Tokens::graft_link.
  • §10.3 says what a count in every: counts: days or weeks.

  • fmt could move a comment twice: placed by where the lines above it were, it moved again once they had been formatted. A comment now sits at most one level inside the line above it, so formatting settles in one pass. The property test found it on a run in CI.

  • The site’s and the VS Code extension’s build tools carried 18 known advisories, 8 of them high: undici, vite, zod, source-map-js and postcss-selector-parser in the site, and MSAL in the extension’s packager. None reached a published page or the extension itself.

  • Two downloaded Python packages that reached the root of the tree in the v1.0 groundwork change are removed.

  • The tree-sitter grammar reads a file whose last line has no line ending, which the new conformance examples found. An external scanner ends a line at a newline or at the end of the file.

  • The GitHub Action’s summary named an unblocked item by a wrong path (plans/bakery/bakery/bakery.sprig) when it checked a folder of folders or a single file. Only a folder one level deep came out right.

  • sprig tui: the tree, next up and the agenda on one screen.

    • Vim keys, a detail pane, and a filter that keeps every match’s ancestors.
    • Ticks, marks, adds and undo through the edit API.
    • Live reload when a file changes, keeping the cursor on its item.
    • A write is refused if its line changed on disk since the TUI showed it, so an editor’s or an agent’s save is never overwritten.
    • --screenshot WxH prints a frame as text, and --keys presses keys first.
  • spec/tools.md T7, and a guide to the TUI.

  • sprig mcp: the plans for coding agents, over the Model Context Protocol.

    • Five read tools return what the matching --json command prints.
    • Five write tools go through the edit API, refuse a change that would add a check error, and return the diff they applied and what stopped waiting.
    • --max-new-items, 20 by default, caps how many items a session may add.
    • --config prints the snippet that registers the server with a client.
  • sprig agent prints the convention for AGENTS.md or CLAUDE.md, and --write FILE keeps it in a marked block there.

  • status --json and check --json.

  • spec/tools.md T6, and a guide to plans for coding agents with a worked session.

  • Tools for the shell, each sharing the core’s edit API or tree:

    • sprig find searches by words, @who, #tag, is:STATE and due:<DATE.
    • sprig agenda shows dated work by day.
    • sprig mark, sprig answer and sprig add change a plan from the command line and say what stopped waiting.
    • sprig edit opens an editor at an item.
    • sprig graph prints the dependencies for Graphviz or Mermaid.
    • sprig export writes JSON, iCalendar or CSV.
    • sprig import reads Markdown checklists, todo.txt and GitHub issues.
    • next --json and find --json print items in the tree format.
  • spec/tools.md T5: what queries mean, the agenda, calendar UIDs, graph ids and conversions.

  • A GitHub Action in action/. It checks plans, annotates problems, and summarises a pull request’s effect on done counts and on what it unblocked.

  • A guide to Sprig in the shell, whose recipes run in CI.

  • Spec draft 0.5:

    • It rules on every ambiguity Appendix B listed, folded into the numbered rules.
    • It states what the text left silent: quoted runs, escaped titles, links that must name a file, answers, indentation whitespace, date shortcuts, est: and every:, month-end recurrence, and due dates and priority that reach down.
    • New warnings: S0006 for an every: that is not a recurrence, S0206 for an after: naming something with nothing to do, and S0007 for a title naming a version of Sprig the tool does not read.
    • Dates have no time of day, an email address is not a person, and the title’s sprig: key is reserved for a future major version.
  • sprig next: open, unblocked work across a folder of plans, in progress first, then priority, then due date, with --who and --limit.

  • sprig check: every problem as file:line:col: severity[code]: message, exit 1 on errors, and on warnings with --strict.

  • --today on every command, so any answer can be reproduced.

  • sprig-core: the parser and resolver. Grafts across files and directories, loops reported once, paths outside the workspace refused, settling, progress, estimates, people and blocking, with no I/O and no clock.

  • spec/diagnostics.md, the catalogue of stable diagnostic codes.

  • spec/tree.schema.json and spec Appendix D, the JSON tree format.

  • tests/conformance/, the conformance suite: 55 examples for lines and indentation, 55 for tokens, fields and dates, and 59 for status, people, blocking and grafts, each section citing every rule it covers.

  • Typed date shortcuts: due:fri, start:+2w, oct3, q4 and the rest of §9.3 resolve against --today.

  • The website runs sprig-core compiled to WebAssembly (109 KB compressed) instead of a JavaScript parser of its own.

  • A command-line reference page on the site, generated from sprig --help, and the first-plan tutorial now ends in the terminal.

  • sprig fmt and sprig fmt --check: two spaces per level, typed dates written out, trailing whitespace gone, and nothing else.

  • sprig tick REF...: done, reopened, or a recurring item’s due date moved on, changing only that byte range. Refs are ^anchor, file^anchor, file:line or words from an item, and - reads them from standard input.

  • sprig_core::edit, a byte-preserving edit API, and spec/tools.md, which states how refs, formatting and edits behave for other implementations.

  • sprig tree, sprig why and sprig status (with --oneline for prompts).

  • --plain on every reading command, tab-separated with a ref first, and --color auto|always|never, which respects NO_COLOR.

  • sprig lsp, a language server built on lsp-server:

    • It republishes diagnostics for every file a change affects, so deleting an anchor flags the files that name it.
    • It completes people, anchors, file links and field keys.
    • It offers go to definition and references for anchors and links.
    • Hover shows progress, the work left, the owner and what an item waits on.
    • Code actions tick an item, cycle its mark and write out a typed date.
    • It formats documents.
  • Editors:

    • a tree-sitter grammar in editors/tree-sitter-sprig, held to the core’s reading of every conformance input;
    • TextMate grammar snapshots;
    • a VS Code extension that bundles the language server;
    • a Neovim setup tested in CI;
    • a guide to setting up each editor.
  • A performance gate: parse, resolve and check on 5,000 lines must stay within twice a committed baseline. Re-inserting a file whose text is unchanged keeps its parse, so a keystroke reparses one file.

  • sprig completions bash|zsh|fish|powershell|elvish, completing refs from the current folder, and sprig man.

  • A dropped item no longer holds up what waits on it: after: is satisfied by a done or a dropped target (spec §5.7). A later item still blocks.
  • An item’s text drops the brackets only of real links; [[my notes]] and [[^a]] stay as written.