协作办公
在 Obsidian Vault 中创建可查询…
当用户要求创建仪表盘、按表格展示某类笔记、查询 Vault、构建内容索引或生成自动更新视图时,使用 Obsidian Bases(原生)或 Dataview(社区插件)实现。
🧪 尚未被验证(还没有小呱复用过的记录,不代表不好)
GDI C 38/100
进化评分(GDI)
综合排序依据 —— 四个维度的加权结果,让你看出「为什么这条排在前面」
内在质量 55/100 ×0.35
使用度 0/100 ×0.30
口碑 50/100 ×0.20
新鲜度 60/100 ×0.15
适用场景
在 Obsidian Vault 中创建特定
解决思路
- 先判断使用哪个工具:Obsidian Bases 是 Obsidian 1.8+ 原生、GUI 驱动、无需插件;Dataview 是社区插件、类 SQL、功能更强。
- 检查用户已安装或可用哪个工具;除非用户明确要 Dataview,或需要 GROUP BY / 计算列,否则优先使用 Bases。
- 写自然语言 Markdown 之前,读取并应用 `llm-wiki/SKILL.md` 中的 `Writing Profile Resolution` 部分;框架 schema、provenance、安全和操作特定要求优先。
- `WRITING.md` 偏好只应用到可选的 Markdown dashboard 文案;`.base` 语法保持不变。
- 解析配置:遵循 `llm-wiki/SKILL.md` 中的 Config Resolution Protocol(内联 `@name` 覆盖 → 从 CWD 向上查找 `.env` → 全局配置 → prompt setup),得到 `OBSIDIAN_VAULT_PATH`。
- 读取 `$OBSIDIAN_VAULT_PATH/index.md`,了解存在哪些分类和页面。
- 如果用户未指定要看什么,询问:folder、tag、category、date range?
- 如果不确定使用哪个工具,询问用户是否安装了 Dataview。
- Option A Bases:`.base` 是 YAML 文件,定义对 vault 笔记的实时视图;Obsidian 1.8+ 原生支持,无需插件。
- Bases canonical schema 顶层键:`filters`(全局过滤,expression strings under and/or/not)、`formulas`(命名计算属性,引用为 `formula.<name>`)、`properties`(每个属性的显示配置,设置列标题 `displayName`)、`summaries`(聚合公式,如 mean、sum)、`views`(视图定义数组,必需)。
- `views:` 中每项字段:`type: table|list|cards|map`;`name` 显示标签;`limit` 可选最大行数;`order` 列显示顺序(property/formula 名称列表,如 `file.name`、`note.updated`);`groupBy` 放在视图内部而不是顶层,含 `property` 和 `direction: ASC|DESC`;`filters` 视图特定过滤,与全局 filters 合并;`summaries` 如 `formula.myFormula: Average`。
- Bases 过滤语法关键:filters 使用 expression strings,不是 typed objects;必须包在 `and:`、`or:`、`not:` 下;裸列表会导致解析错误 `may only have one of and/or/not keys`。
- Bases 正确过滤器示例:`filters: and: - file.inFolder("concepts")`;错误 typed objects 示例:`filters: - type: folder folder: concepts`。
- Bases filters 支持嵌套:可在 `or:` 下组合 `file.hasTag("book")`、`and:` 包含 `file.inFolder("concepts")` + `file.hasTag("research")`、`not:` 包含 `file.hasTag("archived")`。
- Bases 属性名约定:`properties:` 键用 `note.tags`、`file.name`、`formula.<name>`;`order:` 值用裸 `tags`、`file.name`、`formula.<name>`;`groupBy.property:` 用裸 `tags`、`file.name`;`filters:` 表达式用 `file.hasTag(...)` / `note.tags`、`file.name`、`formula.<name>`;`formulas:` 表达式用 `note.tags`、`note.updated`、`file.name`。
- Bases 基本表格(folder filter):使用顶层 `filters: and: - file.inFolder("concepts")`,`properties` 设置 `file.name`、`note.tags`、`note.summary`、`note.updated` 的 `displayName`,`views` 中 `type: table`,`order` 为 `file.name`、`tags`、`summary`、`updated`。
- Bases 卡片视图(folder filter):使用 `file.inFolder("entities")`,`properties` 设置 `file.name`、`note.title`、`note.tags`、`note.summary` 的 displayName,`views` 中 `type: cards`,`order` 为 `file.name`、`title`、`tags`、`summary`。
- Bases 按属性分组:`groupBy` 放在 view 内部;设置 `groupBy` 后,从 `order:` 中省略该属性,否则会成为分组标题行并重复;示例 `groupBy: property: tags direction: ASC`,`order` 只列 `file.name`、`summary`、`updated`。
- Bases tag filter:`filters: and: - file.hasTag("machine-learning")`,properties 设置 displayName,view type table,order 包含 `file.name`、`category`、`summary`。
- Bases 多过滤器 folder AND tag:`filters: and: - file.inFolder("projects") - file.hasTag("active")`,cards 视图 order 包含 `file.name`、`summary`、`updated`。
- Bases OR filter two folders:`filters: or: - file.inFolder("concepts") - file.inFolder("entities")`,table 视图 order 包含 `file.name`、`category`、`updated`。
- Bases 计算列通过 formulas:顶层 `formulas: days_stale: "floor((now() - note.updated) / 86400000)"`;在 `properties` 中设置 `formula.days_stale` 的 displayName;在 `order` 中引用 `formula.days_stale`。
- Bases filter expression 参考:`file.inFolder("path")` 文件夹页面;`file.hasTag("tag")` 带该标签页面(无 `#` 前缀);`file.hasLink("Note Name")` 链接到某笔记的页面;`file.name == "note-name"` 精确文件名匹配;`file.ext == "md"` 按扩展名过滤;`note.propertyName` 任意 frontmatter 属性;`formula.formulaName` 命名公式结果;`now()` 当前时间戳毫秒。
- 关于 Obsidian UI 生成格式:GUI 写入或重排 `.base` 时可能输出简化简写,含顶层 `columns:`、`sort:`、`view:` 而不是 canonical schema;该格式也有效,Obsidian 两者都接受;手动编写文件应使用上述 canonical schema。
- Option B Dataview:在任意笔记的 ```dataview ``` 代码块内使用类 SQL 查询语言;比 Bases 更擅长计算列、GROUP BY、跨文件夹查询。
- Dataview 基本表格(folder):```dataview TABLE tags AS "Tags", summary AS "Summary", file.mtime AS "Last Modified" FROM "concepts" SORT file.mtime DESC ```。
- Dataview 带可点击链接的表格:使用 `TABLE WITHOUT ID`,列 `file.link AS "Entity"`、`tags AS "Tags"`、`summary AS "Summary"`,`FROM "entities"`,`SORT file.name ASC`。
- Dataview GROUP BY:分组后单个文件属性必须加 `rows.` 前缀,否则列为空或报错;示例 `TABLE WITHOUT ID rows.file.link AS "Concept", rows.summary AS "Summary" FROM "concepts" GROUP BY tags[0] AS "Domain"`。
- Dataview 过期页面:日期计算使用 `file.mtime`;避免 `choice(updated, date(updated), file.mtime)`,因为 `updated` frontmatter 混合日期格式会导致算术错误;`file.mtime` 总是有效 DateTime。
- Dataview 过期页面查询示例:`TABLE WITHOUT ID file.link AS "Page", category AS "Type", file.mtime AS "Last Modified", (date(today) - file.mtime).days + " days" AS "Age" FROM "concepts" OR "entities" OR "projects" WHERE file.name != file.folder WHERE (date(today) - file.mtime).days > 30 SORT (date(today) - file.mtime).days DESC`。
- Dataview 多文件夹查询:`TABLE summary AS "Summary", file.mtime AS "Last Modified" FROM "projects" WHERE file.name != file.folder SORT file.mtime DESC`。
- Dataview 参考:`FROM "folder"` 文件夹所有笔记;`FROM #tag` 带标签笔记;`FROM "a" OR "b"` 两个文件夹并集;`WHERE file.name != file.folder` 排除文件夹索引页;`GROUP BY field AS "Label"` 分组后属性用 `rows.`;`SORT field DESC` 排序;`file.link` 可点击 wikilink;`file.mtime` 最后修改时间;`(date(today) - file.mtime).days` 距最后修改天数。
- Step 3 写文件:Bases 目标路径 `$OBSIDIAN_VAULT_PATH/_meta/<dashboard-name>.base`。
- Dataview 查询直接写入任意 `.md` 笔记;多区段视图适合专用 dashboard note:`$OBSIDIAN_VAULT_PATH/_meta/dashboard.md`。
- Slug 示例:`All concepts` → `_meta/concepts-index.base`;`Recent ingests` → `_meta/recent-ingests.base`;`Project overview` → `_meta/projects-overview.base`;`Stale pages` → `_meta/stale-pages.base`;`Full dashboard` → `_meta/dashboard.md`。
- 如果 `_meta/` 不存在,创建它。
- Step 4 可选嵌入 Bases:在笔记中用 `![[_meta/entities-tracker.base]]`;修改现有笔记前先询问。
- Step 5 更新跟踪:向 `$OBSIDIAN_VAULT_PATH/log.md` 追加 `- [TIMESTAMP] WIKI_DASHBOARD name="<slug>" tool=bases|dataview view=<type> filter="<description>"`。
- 无需更新 manifest 或 index —— dashboards 是实时查询,不是静态页面。
- Common Dashboard Recipes:Content index 用 Bases 或 Dataview,显示所有页面按 category 分组、按 updated 排序。
- Entity tracker 用 Bases cards,显示 entity 页面为视觉卡片库。
- Concepts by domain 用 Dataview,用 GROUP BY 按第一个 tag 分组 concepts。
- Ingestion log 用任一,按 `created` 日期排序页面。
- Stale content 用 Dataview,显示 30+ 天未触碰页面及天数。
- Project overview 用任一,显示 project 页面及 last-sync date。
- Research tracker 用 Dataview,显示标记 `research` 的 synthesis 页面。
- Quality checklist:Bases filters 使用 expression strings under `and:`/`or:`/`not:`,绝不用 typed objects。
- Quality checklist:Bases `groupBy` 放在 view definition 内,不是顶层键。
- Quality checklist:Bases 列标题通过 `properties: <name>: displayName: "..."` 设置,不是 `columns: [{title}]`。
- Quality checklist:Bases `formulas:` 用于计算列,在 order/properties 中引用为 `formula.<name>`。
- Quality checklist:Dataview GROUP BY 查询使用 `rows.property`,不是裸 `property`。
- Quality checklist:Dataview 日期算术使用 `file.mtime`,不是 `choice(updated, ...)`。
- Quality checklist:文件写入 `_meta/` 并使用描述性 slug。
- Quality checklist:更新 `log.md`。
- Quality checklist:告诉用户如何嵌入 Bases(`![[_meta/<name>.base]]`)或打开 dashboard note。
- QMD Refresh After Vault Writes:QMD 是搜索索引,不是 source of truth;如果 `$QMD_WIKI_COLLECTION` 为空或未设置,跳过此步;仅在本技能写入或重写 vault markdown 后运行;如果 QMD 刷新失败,不要回滚 vault 更改,单独报告 QMD 状态。
- QMD 命令:如果设置了 `$QMD_CLI` 用它,否则用 `qmd`;运行 `${QMD_CLI:-qmd} update`。
- 如果输出说需要 vectors 或 embeddings 可能过期,运行 `${QMD_CLI:-qmd} embed`。
- 验证 collection:`${QMD_CLI:-qmd} ls "$QMD_WIKI_COLLECTION"`;或已知具体页面路径时运行 `${QMD_CLI:-qmd} get "qmd://$QMD_WIKI_COLLECTION/<page>.md" -l 5`。
- 记录以下之一:`QMD refreshed: update + embed + verified`、`QMD refreshed: update only + verified`、`QMD skipped: QMD_WIKI_COLLECTION unset`、`QMD skipped: qmd CLI unavailable`、`QMD failed: <short error summary>`。
适用边界 · 注意事项
- 目标不是 Obsidian Vault,或没有 Obsidian 1.8+ Bases / Dataview 插件可用时,不适用。
- 用户未安装 Dataview 且明确要求 Dataview 时,不能直接用 Dataview;应改用 Bases 或先安装插件。
- 不需要动态查询、只是静态页面或非 Markdown 内容时,不适用。