feat(knowledge): a run can record what it learned - #85
Merged
Conversation
…ives as its own interface
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What was missing
A run could search and read the knowledge base but had no way to WRITE to it. Nothing taught recording — the tool's description was read-only, no prompt said "record decisions here", and zero notes exist in any project base (only the scaffolded README). The learning a run produced died with the run.
The fix (the action's existence is the teaching)
KnowledgeWriterInterface— the write half, its OWN interface, exactly asKnowledgeBaseInterfacealready promised ("Writing lives on its own interface and is obtained separately, so a palette that must not write cannot be handed a thing that writes"). One method:record(kind, title, body, tags).KnowledgeBaseimplements it — files a markdown note into the kind's folder (decision→decisions/,postmortem→postmortems/,design→design/), with frontmatter tags and an H1 title. The kind→folder map lives here because "where things live" is this class's sole policy. The note is readable immediately; searchable from the next indexing pass (the same read-beats-search lagread()already documents).KnowledgeToolgainsrecord— but ONLY when constructed with a writer: the action is absent from the schema, the description, and the risk level (Safewithout a writer,Mutatingwith) when there is none. A read-only palette is not told writing exists, rather than told not to.IssueRunnerpasses the base as both reader and writer, so a run both consults and records.Correctness details (a clean-context review pass caught these; fixed and tested here):
slug-2.md), never over it — by the base's own conventions a decision that replaces an earlier one is a new note. The claim uses an exclusive create (fopen(..., 'x')), not check-then-write, so it holds under the concurrent runs of one project the base is explicitly designed for.#H1 of its own — a body opening with## Contextstill gets its title, instead of the parser falling back to the filename slug (which rides into every embedded chunk).,[]/newline characters that delimit the frontmatter list, so a stray one cannot mis-file the note.[a-z0-9-], so../../outsidefiles asdesign/outside.md— traversal is not expressible.