Files
roboco/.claude/rules/obsidian-vault.md
2026-07-29 16:38:49 +02:00

4.5 KiB

paths
paths
roboco/services/vault*.py
roboco/vault/**
roboco/vault_assets/**
roboco/foundation/policy/vault_notes.py

Obsidian vault (V1+V2)

Obsidian vault V1+V2 (default-off). The org's human-readable memory palace as a rebuildable DB projection — tasks, journals, and A2A digests as wikilinked markdown — gated by ROBOCO_OBSIDIAN_VAULT_ENABLED + ROBOCO_VAULT_PATH (default off, but both compose files arm it true). VaultWriter (roboco/services/vault_writer.py) is a pure, DB-free materializer under RoboCo/{Tasks/<project-slug>,Journals/<agent-slug>,A2A,Agents,Archive/<year>/Tasks/<project-slug>,Reports}/; every note carries a stable aliases: [<id8>] so a title rename (or an archival move) never breaks a [[id8|title]] cross-link, and private journals are excluded. Four best-effort event seams (TaskService.create's materialize-on-create, TaskService's status-transition frontmatter touch, JournalService, A2AService) patch/append on the relevant transition — a vault write failure never blocks the real action; materialize-on-create means a task's note exists from the moment it's created, not just at curation/rebuild. python -m roboco.vault rebuild re-projects every entity from the DB (preserving an existing task's Auditor-authored ## Narrative, archive-aware so an old terminal task lands directly in Archive/<year>/) and materializes the shipped .obsidian/ config (Dataview, Kanban, graph groups) + RoboCo/_meta/ dashboards + .base Bases views from roboco/vault_assets/; relocate <path> moves the tree, grafting RoboCo/ into an existing personal vault without touching its own config. The Auditor gets a one-shot curate_vault(task_id, narrative) do-tool, spawned by the orchestrator on each completed root task, writing the ## Narrative section a deterministic write otherwise leaves as a placeholder. A second, independently-gated ROBOCO_VAULT_INTAKE_ENABLED watcher (VaultIntakeEngine) turns #roboco-tagged notes under the vault's inbox folder into PENDING, Product-Owner-assigned board-review drafts (source=vault_note) — the identical board-review path a chat-confirmed draft takes, never straight into delivery. Extraction runs on the local model with a deterministic fallback; the note body is screened through foundation/policy/injection_guard.screen_external_text (the same untrusted-content envelope XEngine applies to X mentions — flags an injection-pattern line inline, never removes content) before it reaches the prompt or the fallback. Deduped per (vault-relative path, content hash) via vault_seen_notes, so an edit re-qualifies a previously-seen note — the same hashing convention (every RoboCo feedback callout stripped first, foundation/policy/vault_notes.py) is now shared with the KB engine below. V2 adds three things on top: a drift janitor (services/vault_janitor.py, _vault_janitor_loop) hourly-ticked but gated by a RoboCo/_meta/.janitor_state.json state file so real work (a daily changed-task re-projection + random-sample drift check + archival pass, each capped at 200/cycle and per-item isolated so one bad row never wedges the sweep) and a weekly org-report (vault_report_enabled, default true — VaultWriter.write_org_report from MetricsService/UsageService, best-effort CEO notification) each fire exactly once per elapsed period regardless of loop/restart cadence; archival (vault_archive_days, default 30, 0=off) moving old terminal tasks' notes into RoboCo/Archive/<year>/Tasks/<project>/ during the sweep, alias links making the move free and the shipped Dataview/graph assets Archive/-aware; and KB ingest (vault_kb_enabled, default false — NAS compose arms it true, registry compose leaves it false) embedding the CEO's own RoboCo/Notes/ (config vault_kb_dirs, csv, load-time-validated against traversal/overlap with reserved projection dirs) into a new IndexType.VAULT_NOTES corpus via _vault_kb_loop (services/vault_kb_engine.py, default 900s), with every note re-checked for symlink/path-escape at read time and screened through the injection guard as a hard GATE (a flagged note is quarantined — skipped, logged, callout-marked, never embedded) rather than the intake watcher's screen-and-still-process posture — reaching roboco_kb_search, MentorService's default domain, and EvidenceRepo.similar_memory (claim-time briefings, relevance-floored, labeled vault_note) so the CEO's own writing finally becomes fleet-retrievable institutional memory.