T-NLKF-converge-obsidian-bases
Status: closed/done · Impact: medium · Complexity: large
The monorepo carries two independent implementations of the same idea:
@sksizer/obsidian-bases (packages/ts/obsidian-bases/ — the canonical
one) and the vendored @augment/obsidian-bases
(packages/ts/obsidian-bases-augment/, brought over by T-LVLY as an
explicitly temporary bridge). Port every @augment consumer onto the
@sksizer implementation and delete the duplicate. This is the core
“share libraries” payoff of the adoption.
| Location | Role today |
|---|---|
packages/ts/obsidian-bases/src/index.ts | @sksizer/obsidian-bases public surface: .base parsing, filters, formulas, views over a markdown vault (src/base/, src/expr/, src/query.ts, src/vault/) |
packages/ts/obsidian-bases-augment/ | The vendored duplicate (exists once T-LVLY lands); README banner names this task as its deletion |
packages/ts/obsidian-bases-augment/demo/ | Its Nuxt demo (exists once T-UPV1 lands) — the only real consumer |
package.json | Root workspaces carries the demo’s entry, which must be repointed when the demo moves |
Consumer surface, from a grep of the source repo at pinned rev
acedcf77652e2e7c481e95123c486c2befe2c423 (all inside the
obsidian-bases demo):
Used @augment symbol | Site (within the demo) |
|---|---|
VaultDatabase, FileIndexer, QueryBuilder | server/utils/vault-manager.ts |
parseExpression, parseBaseFile | server/api/query.post.ts |
Filter, SortOrder (types) | server/api/query.post.ts |
IndexedNote (type) | app/app.vue |
augmented_web declared the dep without importing it; T-KTGF drops it
with grep proof. If that verification instead found real usage, this task
inherits those sites too.
Proposed
Section titled “Proposed”- The demo lives at
packages/ts/obsidian-bases/demo/and runs entirely on@sksizer/obsidian-bases. packages/ts/obsidian-bases-augment/is deleted.- No
@augment/obsidian-basesstring remains anywhere in the repo (deps or imports). - Any capability the demo needed that
@sksizer/obsidian-baseslacked exists there now as a tested, exported API — extend the canonical package rather than keeping the fork alive.
Approach
Section titled “Approach”- Enumerate the exact exports of
@sksizer/obsidian-bases(src/index.ts) and map each used@augmentsymbol from the table above to its counterpart:parseBaseFile→ thesrc/base/parser,parseExpression→src/expr/,VaultDatabase/FileIndexer→src/vault/indexing,QueryBuilder→src/query.ts, plus theFilter/SortOrder/IndexedNotetype equivalents. - For each gap (no counterpart, or shape mismatch a thin adapter can’t
bridge): add a minimal exported API to
@sksizer/obsidian-baseswith tests. Additive changes only — no breaking changes to existing consumers of the package. - Port the demo’s
server/utils/vault-manager.ts,server/api/query.post.ts, andapp/app.vueonto the mapped APIs; keep itsvaults/fixtures as the functional check. - Move the demo dir
packages/ts/obsidian-bases-augment/demo/→packages/ts/obsidian-bases/demo/; update the rootworkspacesentry. - Delete
packages/ts/obsidian-bases-augment/. - Sweep:
grep -r "@augment/obsidian-bases"over the repo must return nothing outside git history.
Files to touch
Section titled “Files to touch”| Location | Kind | Change |
|---|---|---|
packages/ts/obsidian-bases/src/ | modify | Additive exports + tests for any mapped gaps |
packages/ts/obsidian-bases/demo/ | new | The demo, relocated and ported to @sksizer/obsidian-bases |
packages/ts/obsidian-bases-augment/ | delete | The duplicate implementation and its README banner |
package.json | modify | Repoint the demo’s workspaces entry |
bun.lock | modify | Workspace membership change |
Acceptance criteria
Section titled “Acceptance criteria”- AC-1:
grep -r "@augment/obsidian-bases" --exclude-dir=node_modulesover the repo returns nothing. - AC-2:
packages/ts/obsidian-bases-augment/no longer exists. - AC-3: The relocated demo builds, and its query API boots and
answers against the
vaults/fixtures. - AC-4:
bun testpasses inpackages/ts/obsidian-bases/, including tests for any newly added exports. - AC-5: Existing
@sksizer/obsidian-basesconsumers are untouched (no breaking API changes).
Out of scope
Section titled “Out of scope”- Porting
@sksizer/obsidian-basesfeatures into the deleted fork (direction is one-way). - Broader vault-tooling convergence (
vault-path,dir-aspect) —T-JCML.
Dependencies
Section titled “Dependencies”T-KTGF— resolves whether augmented_web is a real consumer.T-UPV1— lands the demo this task ports.
Discovery context
Section titled “Discovery context”- Duplicate spotted during adoption planning 2026-07-18: the two implementations share the goal but not the code (different module layouts, no common history).
Post-mortem
Section titled “Post-mortem”Captured by /sdlc:task-work on 2026-07-19. PR: pending.
Acceptance criteria coverage
Section titled “Acceptance criteria coverage”- AC-1: agent-manual —
git grep -n "@augment/obsidian-bases"clean across all code/deps/imports/config;grep -con regeneratedbun.lock= 0. The literal string remains only in fourdocs/planning/tasks/specs (this task plus siblingsT-KTGF/T-LVLY/T-UPV1), which the## Proposedscoping (“no@augment/obsidian-basesstring remains … (deps or imports)”) and the “git history is fine” carve-out place out of scope. (deferred-user — confirm the planning-prose references are acceptable, or decide to scrub the siblings separately.) - AC-2: agent-manual —
packages/ts/obsidian-bases-augment/no longer exists (git rm -r); verified absent. - AC-3: agent-manual —
bun run buildin the relocated demo exits 0 (Nitro bundle incl. portedquery.post/vault-indexroutes); a functional driver script ran the portedvault-manager+query-runneragainst the realvaults/fixtures across all three query modes and returned correct non-empty results; stricttsc --noEmiton the ported server TS passed. (deferred-user — full Nuxt SFC-levelvue-tsc/nuxi typecheckcould not run in the sandbox; spot-check the demo UI.) - AC-4: auto —
bun testinpackages/ts/obsidian-bases/: 98 pass / 0 fail (92 pre-existing + 6 newqueryVaulttests insrc/query.test.ts). - AC-5: auto — additive exports only; no existing export signature changed;
tsc --noEmitclean; all 92 pre-existing package tests still pass.
What worked
Section titled “What worked”- The one genuine capability gap (paged/sorted ad-hoc query) collapsed to a single small tested
export (
queryVault); the rest of the OO→functional port bridged cleanly via existing@sksizerexports (scanVault,parseBase,parseExpression,runView). - A demo-side DTO adapter (
noteToDto) projectedVaultNoteonto the UI’s expected shape, soapp.vue(~1500 lines) changed only its import source — no UI rewrite. - The baseline-gated quality gate came back
OK 10/10with zero new drift, cleanly separating this branch’s changes from the 13 pre-existingbun test ./.claudefindings.
Friction and automation gaps
Section titled “Friction and automation gaps”- Repo-wide pre-commit hook
project-check-task-state-originfailed on an unrelated active branch (task/T-AZKG’s stray state-only “record PR” commit), blocking commits on every branch — worked around withLEFTHOOK_EXCLUDE=project-check-task-state-origin— the check should scope to the branch being committed (or to HEAD’s ancestry) rather than failing globally on another live session’s branch; alternatively Step 10.4’sappend_pr_urlmust reliably land theprs:commit on main, never on a task branch. → T-WLNF-scope-task-state-origin-to-branch - The
autonomy: autonomous/prauto-define body edit (path-citation fix) committed on the task branch is discarded bystart_task’sreset --hard origin/main, so it never persists and the readiness stamp lands on main against the still-original body — task-work’s Step 5a auto-define should land its body edit onorigin/main(as the stamp does) so it survives the reset and main stays self-consistent. → T-RNHP-autonomy-body-fill-lands-on-main - Step 3a captured the quality baseline into the main repo’s
.sdlc/quality-baselines/but Step 7’s gate defaulted to the worktree’s.sdlc/and erroredbaseline not found— task-work Step 7 should pass--baseline-dir <main-repo>/.sdlc/quality-baselinesby default since.sdlc/is per-worktree and the baseline is captured in the superproject. → T-F1WJ-quality-run-resolves-superproject-baseline - The pre-commit hook is slow (~2-3 min;
project-check-apps-importsscans all monorepo apps), timing out a foreground commit at the 2-min tool limit — the apps-imports check could scope to staged paths. → T-W6NY-apps-imports-check-scopes-to-staged - AC-1 as written (“grep … returns nothing”) conflicts with the
## Proposed“(deps or imports)” scoping and with the planning-prose references that must survive — future sweep-style ACs should state the exclusion inline (e.g. “outsidedocs/planning/and git history”). → T-12HH-sweep-acs-state-exclusions-inline
Spawned follow-up tasks
Section titled “Spawned follow-up tasks”- T-WLNF-scope-task-state-origin-to-branch (https://github.com/sksizer/dev/pull/941)
[open/ready] — scope
project-check-task-state-originto the committed branch (or HEAD ancestry) so it stops failing globally on another session’s branch; spawned. - T-RNHP-autonomy-body-fill-lands-on-main [open/ready] — route the autonomy auto-define
body edit to
origin/mainsostart_task’s reset preserves it; linked (existing task). - T-F1WJ-quality-run-resolves-superproject-baseline [planning/draft] — resolve the
superproject’s quality-baseline dir when
quality runis invoked from a worktree; linked (existing task). - T-W6NY-apps-imports-check-scopes-to-staged (https://github.com/sksizer/dev/pull/942)
[open/ready] — scope
project-check-apps-importsto staged paths so the pre-commit hook stops scanning all monorepo apps; spawned. - T-12HH-sweep-acs-state-exclusions-inline (https://github.com/sksizer/dev/pull/943) [open/ready] — make sweep/grep-style acceptance criteria state their exclusions inline; spawned.
Depends on
Section titled “Depends on”T-KTGF, T-UPV1