All notable changes to this project will be documented in this file.
The format is based on Keep a Changelog, and this project adheres to Semantic Versioning.
0.3.0 - 2026-05-28
Fixes a silent-empty-result failure for suffix-timestamped archives (Title 202506252102.md) and makes note ID detection configurable. Adds layered wiki-link resolution and a global --verbose flag so pipeline decisions are observable on stderr.
- Configurable note ID detection. The default pattern is now the unanchored regex
\d{12}, a strict superset of the previous prefix-only behavior. Prefix (202503091430 Title.md), suffix (Title 202506252102.md), and mid-filename layouts all index correctly with no config required. See ADR-006. id_patternconfig key in~/.config/ta/config.yamlfor custom schemes (14-digitYYYYMMDDHHMMSS, alphanumeric IDs, project-specific patterns). Invalid regexes fall back to the default with a verbose-mode warning rather than crashing.- Layered wiki-link resolution.
[[target]]resolves in three tiers: exact ID → filename substring (case-insensitive, Archive-style) → unambiguous ID prefix.[[Cognitive Distancing]]now resolves toThinking About Thinking - Cognitive Distancing 202506252102.mdwhen the substring is unique. --verboseglobal flag on every subcommand (search,tag,show). Logs pipeline decisions to stderr: resolved config (archive path + id_pattern + provenance), file-scan skips with reasons, ripgrep commands and match counts, structural verification, graph expansion depth, and wiki-link resolution method. Defaults to off; stdout is unchanged.- ADR-006 documenting the ID-detection redesign and alternatives considered.
NoteIndexindexes filename stems alongside extracted IDs, enabling substring-based wiki-link resolution. All non-overlapping matches of the ID pattern in a filename become index keys (a file with two 12-digit runs is reachable via either).NoteParserextracts the timestamp ID position-agnostically. Title extraction no longer requires a 12-digit prefix; suffix-timestamped notes get the correct title and ID.- Pipeline plumbing.
SearchPipeline,ShowPipeline, and the runners accept aResolvedConfig(archive + id_pattern + provenance) and an optionalLoggerso verbose mode reaches every layer.
- New
IDPatterntype wraps a configurable regex extractor (Sources/ta/Config/IDPattern.swift). - New
ResolvedConfigbundles archive directory, ID pattern, and provenance for downstream consumers (Sources/ta/Config/ResolvedConfig.swift). - New
Loggertype with injectable sink for stderr diagnostics (Sources/ta/Logging/Logger.swift). - Dead
NoteIndex.extractTimestampPrefixremoved;IDPattern.extractIDs(from:)is the replacement. - 33 new tests across
IDPatternTests,ArchiveResolverTests,LoggerTests,NoteIndexTests,NoteParserTests,SubstringResolutionTests,IntegrationTests,GraphExpanderTests,RipgrepRunnerTests,StructuralFilterTests, andSearchCommandTests. The suite is now 112 tests across 19 suites.
0.2.0 - 2026-05-13
Search now finds matches it previously hid: text inside Markdown inline-code spans (e.g. `LSUIElement`), notes stored as .txt, and queries that don't match the casing of the source.
.txtnotes are indexed alongside.md.NoteIndexenumerates both extensions and the supported set is centralized atNoteIndex.supportedExtensions. Adding a third extension is now a one-line change.ta showalready worked on.txtfiles via byte-for-byte body emission; this commit makes them discoverable byta searchandta tag.ParsedNote.rawTextcarries the original source string alongside the existingnonCodeTextprojection.
ta search's--wordand--phrasepredicates now match inside inline-code spans. Previously, terms wrapped in backticks (e.g.`LSUIElement`) were stripped before search and invisible to all predicates. Word and phrase predicates now match against the raw note text. Hashtag matching (--tag) still respects inline-code stripping —#fooinside backticks is not counted as a tag, and[[link]]inside backticks is not counted as a wiki link.- All predicates (
--tag,--phrase,--word) are now case-insensitive.ta search --word lsuielementfindsLSUIElement;ta search --tag macosfinds#MacOS. Both the ripgrep/grep candidate-selection layer and the in-process structural filter use case-insensitive matching consistently. - Snippets in search output come from the raw note text, so the surrounding context shown to the user matches what they would see in the file (including any backticks).
RipgrepRunnerderives its-g/--includeflags fromNoteIndex.supportedExtensionsrather than hardcoding*.md.NoteParser.titleFromFilenameusesNSString.deletingPathExtensioninstead of magic-numberedremoveLast(3|4)branches.- 7 new tests across
NoteIndexTests,RipgrepRunnerTests,StructuralFilterTests, andIntegrationTests; the suite is now 79 tests across 16 suites.
0.1.0 - 2026-04-17
First prototype release of ta — a command-line retrieval tool over a Zettelkasten archive, shaped for coding agents.
ta searchsubcommand — AND-combined predicates (--tag,--phrase,--word, positional phrase),--depth Ngraph expansion (default 3, cap 10). Emits flat YAML list of hits withref,title,snippet,tags,links,depth,viafields per ADR-004.ta tag NAMEsubcommand — convenience forta search --tag NAME.ta show REF...subcommand — emits YAML frontmatter + raw markdown body per ref,---delimited. Partial-success exit handling (exit 0 if any ref resolved, 1 if none) per ADR-005.- Cold-start pipeline — ripgrep candidate selection → swift-markdown AST walk → hashtag and wiki-link regex extraction on non-code text → BFS graph expansion with cycle dedup → YAML emission. No in-memory index between invocations.
- Hashtag recognition — Unicode-aware regex per ADR-002. Rejects URL fragments and word-adjacent
#; accepts hyphens and underscores mid-tag. - Wiki-link recognition —
[[target]]and[[target|anchor]]per ADR-001. Resolves via exact 12-digit timestamp prefix → unambiguous prefix match → unresolved. - Code-block exclusion — tags and wiki-links inside fenced/indented code blocks and inline code are never recognized as structural markers.
- Archive resolution — precedence flag
--archive PATHon a subcommand →TA_DIRenv var →archive:key in~/.config/ta/config.yaml. - Grep fallback — falls back to
grep -l -rwhenrgis absent fromPATH. - Symlink resolution — archive paths that are symlinks resolve correctly before directory enumeration.
- Agent-friendly help and error messages — root
--helpand each subcommand's--helpshow runnable examples; error paths (missing predicates, missing refs, unresolved archive, tool-not-found) include copy-pasteable next steps. - Agent skills bundle under
docs/skills/— three copy-pasteable skills for coding agents:ta-search(literal lookups),ta-associative-recall(fan-out recall for fuzzy queries),ta-deep-research(graph crawl + synthesis). - Design documentation — design spec, implementation plan, and ADRs 001–005.
- 72 tests across 16 suites, including end-to-end integration tests over a 13-note fixture archive.