
Obos
- 5 installs
- Updated February 16, 2026
- hamsterider-m/obsidian-best-pract
Manage an Obsidian vault via /obos commands: capture ideas to inbox, tidy and file notes, sync the index, and review vault health.
About
An opinionated Obsidian vault management system built on a collect-organize-connect-review loop driven by /obos commands. A developer uses it to capture insights, tidy files, sync the index, and review vault health.
- Core loop: save to inbox, tidy, sync index, review
- Commands for init, multi-vault registry, refine, ask, and draft
Obos by the numbers
- 5 all-time installs (skills.sh)
- Ranked #2,303 of 3,282 Productivity & Planning skills by installs in the Skillselion catalog
- Data as of Aug 2, 2026 (Skillselion catalog sync)
npx skills add https://github.com/hamsterider-m/obsidian-best-pract --skill obosAdd your badge
Show developers this skill is listed on Skillselion. Paste this into your README.
| Installs | 5 |
|---|---|
| Last updated | February 16, 2026 |
| Repository | hamsterider-m/obsidian-best-pract ↗ |
What it does
Manage an Obsidian vault via /obos commands: capture ideas to inbox, tidy and file notes, sync the index, and review vault health.
Files
Obsidian Best Practices (obos)
有主见的 Obsidian vault 管理系统。核心循环:收集 → 整理 → 连接 → 回顾。
Commands
| Command | Description |
|---|---|
/obos save ["内容"] | 快速收集想法到 Inbox(核心命令) |
/obos tidy | 整理笔记归位(支持 standard/strong 模式) |
/obos sync | 更新索引 + 健康报告 + 链接建议 |
/obos review | Vault 状态回顾 + 下一步建议 |
/obos init | 初始化 vault 结构 |
/obos vault | 管理多个 vault 注册 |
/obos refine [note] | 深度加工笔记(进阶) |
/obos ask "question" | 查询知识库(进阶) |
/obos draft "topic" | 基于笔记起草文章(进阶) |
No argument → show grouped command list:
核心:save, tidy, sync, review
设置:init, vault
进阶:refine, ask, draftTidy 默认策略
/obos tidy 默认按 standard 模式运行,并启用幂等增量整理:
- 重复执行时,已整理且未变更的文件会被跳过,不重复迁移
- 自动重命名默认只执行一次;检测到手动改名后自动锁定(
name_locked: true) - 项目目录默认
project-policy=contain:项目结构冻结,不打散且不改内部层级/文件名 - 通过
/.obos/tidy-state.json与 frontmatter 双重判定稳定性 - 通过
/.obos/tidy-config.json可扩展项目目录白名单(projectRootsExtra) - strong 模式先进行目录必要性评估(KEEP / REORGANIZE / ARCHIVE_DIR)
- 目录评估审计输出到
/.obos/dir-audit.json - 默认不删除 markdown 文档(
deleteMarkdown=false),仅清理空目录
Multi-Vault 配置
配置文件:~/.proma/agent-workspaces/obsidian/obos-config.json
{
"vaults": {
"personal": { "path": "D:/obsidian/personal", "default": true },
"work": { "path": "C:/Users/.../work-vault" }
},
"lastUsedVault": "personal"
}Vault Path Discovery
所有命令共享此逻辑(按优先级):
1. 命令参数 --to <alias> 指定的 vault 2. obos-config.json 中的 default vault 3. 当前工作目录(如果包含 .obsidian/ 或 vault CLAUDE.md) 4. 如果以上都不存在,用 AskUserQuestion 引导用户注册 vault
Vault Structure
Vault/
├── CLAUDE.md # AI context file
├── Index.md # AI-readable index (auto-generated)
├── Inbox/ # 收集入口(save 写入此处)
├── Notes/ # Evergreen notes
├── Clippings/ # Web clippings
├── References/ # Source materials
├── Attachments/ # Images and files
├── Categories/ # MOC index pages
└── Templates/ # Note templatesKnowledge Maturity Model
Frontmatter status 字段:
inbox— 刚收集,未整理draft— 已分类,未深度加工refined— 经过/obos refine深度加工
Evergreen Note Template
---
status: {{inbox|draft|refined}}
source: {{attribution}}
created: {{YYYY-MM-DD}}
---
# {{title}}
## Core Idea
One sentence in your own words.
## My Understanding
Why it matters. What you agree/disagree with.
## Open Questions
What new questions does this raise?
## Related
- [[]]Command Routing
Parse the first argument after /obos and load the matching commands/{command}.md file. If no argument, show the grouped command list above and ask what the user wants to do.
/obos ask "question"
Query your knowledge base using keyword search and AI synthesis.
Usage
/obos ask "question"Vault Path Discovery
Resolve vault location per shared logic in SKILL.md: 1. Current working directory (if has CLAUDE.md or .obsidian/) 2. Fallback path 3. Ask user
Behavior
Step 1: Parse Question
Extract keywords and key phrases from the user's question. Identify the core intent: factual lookup, conceptual exploration, or cross-reference.
Step 2: Search Index.md
Read Index.md at vault root to locate candidate notes. Scan the Recent Notes table and Categories section for keyword matches.
If Index.md yields fewer than 3 candidates, expand search:
- Use Glob to scan
Notes/,Clippings/,References/for filename matches - Use Grep to search file contents for keyword hits
Rank candidates by relevance (title match > content match > category match).
Step 3: Read Top Notes
Read up to 5 most relevant notes in full. Extract key passages that address the question.
Step 4: Synthesize Answer
Compose a concise answer that:
- Directly addresses the question
- Cites each source with
[[wikilink]]notation - Distinguishes between direct quotes and paraphrased content
Format:
{answer text} ([[Source Note 1]], [[Source Note 2]])
**Sources**:
- [[Source Note 1]] - {why relevant}
- [[Source Note 2]] - {why relevant}Step 5: No Match Handling
If no relevant notes are found, respond with graceful degradation:
知识库中暂无相关内容。
Suggest next steps:
- Rephrase the question with different keywords
- Use
/obos saveto capture new knowledge on this topic - Use
/obos syncto ensure Index.md is up to date
/obos draft "topic"
Writing assist: generate outlines and drafts based on your existing notes.
Usage
/obos draft "topic" # generate outline with writing prompts
/obos draft "topic" --assist # AI generates draft sectionsParameters
| Param | Description |
|---|---|
"topic" | The writing topic or title (required) |
--assist | Let AI generate prose for selected sections |
Vault Path Discovery
Use Vault Path Discovery from SKILL.md to determine vault root.
Behavior
Step 1: Search Related Notes
Reuse the search logic from /obos ask:
1. Extract keywords from the topic 2. Read Index.md to locate candidate notes 3. If fewer than 3 candidates, expand with Glob + Grep across Notes/, Clippings/, References/ 4. Rank by relevance (title match > content match > category match) 5. Read up to 5 most relevant notes in full
Step 2: Present Source Materials
Display found materials for user review:
找到以下相关素材:
1. [[Note A]] - {brief summary, why relevant}
2. [[Note B]] - {brief summary, why relevant}
3. [[Note C]] - {brief summary, why relevant}
是否需要增删素材?Use AskUserQuestion:
- "继续生成大纲" (Recommended)
- "增加素材" — user specifies additional notes to include
- "移除素材" — user picks notes to exclude
Step 3: Generate Outline (Default Mode)
Create a structured outline with writing prompts for each section:
# {Topic}
## 1. {Section Title}
> 素材来源:[[Note A]]
> 写作提示:{what to cover, key argument to develop}
## 2. {Section Title}
> 素材来源:[[Note B]], [[Note C]]
> 写作提示:{what to cover, how sources connect}
## 3. {Section Title}
> 素材来源:[[Note A]]
> 写作提示:{what to cover, open questions to address}
## Conclusion
> 写作提示:{how to tie sections together, key takeaway}Each section includes:
- A clear heading
- Source attribution (
素材来源) with[[wikilinks]] - A writing prompt (
写作提示) guiding what to write
Step 4: Assist Mode (--assist)
When --assist is provided, after generating the outline:
1. Ask user which section(s) to draft via AskUserQuestion
- List section titles as options
- Allow multiple selection
2. For each selected section, generate prose:
- Draw from the source notes' content
- Maintain the user's voice (match style of existing notes)
- Mark AI-generated content clearly:
<!-- AI-assisted draft — review and revise -->3. Present the draft for user review before writing to file
Step 5: Save Draft
Write the outline (or outline + drafted sections) to Notes/{topic}.md:
---
status: draft
source: draft from vault notes
created: {YYYY-MM-DD}
---
# {Topic}
{outline or drafted content}
## Sources
- [[Note A]] - {contribution}
- [[Note B]] - {contribution}Success Message
- Draft outline created:
Notes/{topic}.md - Sections: {count}
- Source notes used: {count}
- Status: draft
- Tip: Use
--assistto generate prose for specific sections, then/obos refinewhen ready
/obos init
初始化 Obsidian vault 结构并注册到多 vault 配置。幂等执行,重复运行不会覆盖已有内容。
Usage
/obos init # 初始化当前目录或默认 vault
/obos init <path> # 初始化指定路径Step 1: 确定 Vault 路径
优先级: 1. 命令参数指定的 <path> 2. 当前工作目录(如果包含 .obsidian/) 3. 用 AskUserQuestion 询问用户 vault 路径
Step 2: 扫描现有结构
扫描 vault 目录,检测已有目录模式:
| 已有目录 | 建议映射 | 说明 |
|---|---|---|
Journal/, Diary/, 日记/ | Inbox/ 或保留 | 建议作为历史内容保留 |
Inbox/, Fleeting/ | Inbox/ | 直接复用 |
Assets/, Images/, Media/ | Attachments/ | 建议重命名 |
Sources/, Literature/ | References/ | 建议重命名 |
MOC/, Maps/, Index/ | Categories/ | 建议重命名 |
如果检测到已有目录,用 AskUserQuestion 询问:
- "重命名为标准名称"
- "保留现有名称"
- "跳过"
插件冲突检测:检查 .obsidian/plugins/ 是否有 Daily Notes 或 Periodic Notes 插件,如有则提示用户注意。
Step 3: 创建目录(幂等)
标准目录列表(已存在则跳过):
Inbox/ # 收集入口
Notes/ # Evergreen notes
Clippings/ # Web clippings
References/ # Source materials
Attachments/ # Images and files
Categories/ # MOC index pages
Templates/ # Note templatesStep 4: 生成 CLAUDE.md
已存在 → 跳过,不覆盖。
不存在则创建:
# CLAUDE.md
This file teaches AI assistants about this knowledge vault.
## About This Vault
{{VAULT_PURPOSE}}
## Structure
- `Inbox/` - 收集入口,未整理的想法和笔记
- `Notes/` - Evergreen notes (atomic, linked ideas)
- `Clippings/` - Web clippings and highlights
- `References/` - Source materials (books, articles)
- `Categories/` - MOC (Map of Content) index pages
- `Attachments/` - Images and files
## Conventions
- Note titles: Descriptive, noun phrases
- Links: Use `[[wikilinks]]`
- Tags: Minimal, prefer links over tags
## Key Topics
{{KEY_TOPICS}}
## Active Projects
{{ACTIVE_PROJECTS}}Step 5: 交互式引导(AskUserQuestion)
填充 CLAUDE.md 占位符:
Q1 — Vault 用途:
"这个 vault 的主要用途是什么?"
Options: "个人知识管理", "工作项目笔记", "学习与研究", "写作与创作", "混合用途"
Q2 — 关注领域:
"你最关注的 2-3 个领域是什么?"
根据 Q1 答案提供示例选项 + "自定义输入"
Q3 — 活跃项目(可选):
"当前有进行中的项目吗?"
Options: "有,我来填写", "暂时没有"
用回答替换 CLAUDE.md 中的占位符。
Step 6: 生成 Index.md
已存在 → 跳过。
不存在则创建:
# Index
AI-readable index of vault contents. Auto-generated by `/obos sync`.
## Recent Notes
(empty — run `/obos sync` to populate)
## Categories
(empty — run `/obos sync` to populate)
## Statistics
- Total notes: 0
- Last synced: neverStep 7: 创建模板
创建 Templates/Evergreen.md(如不存在),使用 SKILL.md 中的 Evergreen Note Template。
Step 8: 注册 Vault
读取 obos-config.json,如果当前 vault 未注册: 1. 用 AskUserQuestion 询问别名:"给这个 vault 起个别名(如 personal、work)" 2. 写入配置文件 3. 如果是第一个 vault,自动设为 default
Output
✅ Vault 初始化完成:[vault_path]
目录:
[✓] Inbox/ — 已创建 | 已存在
[✓] Notes/ — 已创建 | 已存在
[✓] Clippings/ — 已创建 | 已存在
[✓] References/ — 已创建 | 已存在
[✓] Attachments/ — 已创建 | 已存在
[✓] Categories/ — 已创建 | 已存在
[✓] Templates/ — 已创建 | 已存在
文件:
[✓] CLAUDE.md — 已生成 | 已存在(未覆盖)
[✓] Index.md — 已生成 | 已存在(未覆盖)
[✓] Templates/Evergreen.md
Vault 已注册为: <alias>
下一步:
- 运行 /obos save 收集你的第一个想法
- 运行 /obos tidy 整理已有的散落文件
- 运行 /obos sync 生成索引/obos refine
Socratic note refinement: transform draft notes into refined evergreen notes through guided conversation.
Usage
/obos refine [note]note— filename or wikilink (e.g.My Noteor[[My Note]])- If omitted, infer target from current conversation context
Interaction Mode
This command uses conversational dialogue (对话式交互), NOT AskUserQuestion. Open-ended text input requires natural conversation turns.
Behavior
Step 1: Identify Vault Path
Use Vault Path Discovery from SKILL.md: 1. Current working directory (if has CLAUDE.md or .obsidian/) 2. Fallback: /Users/hansonmei/OneDrive/obsidian-vault/ 3. If neither exists, ask user
Step 2: Read Target Note
- If
[note]parameter provided, locate file in vault (searchNotes/,Daily/,Clippings/) - If omitted, infer from conversation context
- If not found, list recent draft notes and let user pick
Display the note content to the user.
Step 3: Extract Key Points
Analyze the note and present a brief summary:
- Main argument or idea
- Supporting points
- Current gaps or ambiguities
Step 4: Socratic Three Questions
Conduct three conversation turns. Wait for user response after each question.
Turn 1 — Restate (复述):
用你自己的话,核心观点是什么?
Turn 2 — Evaluate (评判):
你同意吗?有什么保留意见?
Turn 3 — Connect (关联):
这和你已有的哪些知识相关?
Step 5: Generate Refined Evergreen Note
Based on user's three answers, generate a note using the Evergreen Note Template from SKILL.md:
---
status: refined
source: {original note attribution}
created: {YYYY-MM-DD}
---
# {Title}
## Core Idea
{User's own restatement from Turn 1}
## My Understanding
{User's evaluation from Turn 2}
## Open Questions
{New questions raised during dialogue}
## Related
- [[{connections from Turn 3}]]
- [[{original note backlink}]]Step 6: Write and Update
1. Write refined note to Notes/{title}.md 2. Update frontmatter status to refined per Knowledge Maturity Model from SKILL.md 3. Add backlink in original note pointing to the new evergreen note 4. Suggest running /obos sync to update Index.md
Success Message
- Refined note created:
Notes/{title}.md - Status: draft → refined
- Backlinks: added
- Tip: Run
/obos syncto update your index
/obos review
Vault 状态回顾,不绑定时间周期,随时可以运行。输出 vault 健康度和下一步行动建议。
Usage
/obos review # 回顾默认 vault
/obos review --to work # 回顾指定 vaultStep 1: 确定目标 Vault
使用 SKILL.md 中的 Vault Path Discovery 逻辑。
Step 2: 收集数据
读取 vault 中的关键信息:
1. Index.md — 如果存在,读取统计数据和最近笔记 2. Inbox/ 目录 — 统计未整理文件数量 3. 各标准目录 — 统计文件数量 4. frontmatter 扫描 — 统计各 status 的笔记数量(inbox/draft/refined) 5. 最近 7 天 — 新增和修改的文件列表
Step 3: 输出回顾报告
📊 Vault 回顾: {vault_alias}
═══════════════════════════
总笔记: {count}
Inbox: {n} | Notes: {n} | Clippings: {n} | References: {n}
成熟度:
██████░░░░ inbox: {n}
████░░░░░░ draft: {n}
██░░░░░░░░ refined: {n}
最近 7 天动态:
新增: {n} 篇
修改: {n} 篇
{列出最近 5 个文件名和目录}Step 4: 待处理事项
根据 vault 状态,列出需要关注的事项:
待处理:
📥 Inbox 未整理: {n} 篇 → /obos tidy
🏝️ 孤岛笔记: {n} 篇 → /obos sync
📝 Draft 笔记: {n} 篇 → /obos refine只显示数量 > 0 的项目。如果全部为 0,输出:
✅ Vault 状态良好,没有待处理事项。Step 5: 下一步建议
根据优先级给出一个最有价值的行动建议:
1. Inbox 有未整理文件 → "建议先运行 /obos tidy 整理 {n} 篇 Inbox 笔记" 2. 孤岛笔记多 → "建议运行 /obos sync 为孤岛笔记建立链接" 3. Draft 笔记多 → "可以挑一篇运行 /obos refine 深度加工" 4. 都没有 → "Vault 井然有序。随时用 /obos save 收集新想法"
只给一条建议,不要列出所有可能的操作。
/obos save
核心命令。快速收集想法到 vault 的 Inbox 目录。
Usage
/obos save "想法或内容" # 直接存入默认 vault
/obos save "内容" --to work # 存入指定 vault
/obos save # 从当前对话上下文自动提取Step 1: 确定目标 Vault
按优先级: 1. --to <alias> 参数指定 2. obos-config.json 中的 default vault 3. 如果无配置,用 AskUserQuestion 引导注册(参考 vault.md)
确定后更新 lastUsedVault。
Step 2: 提取内容
有参数:使用用户传入的文本作为原始内容。
无参数:分析当前对话上下文,提取:
- 关键结论或洞见
- 决策和理由
- 值得记录的想法
如果对话中没有明显可提取的内容,用 AskUserQuestion 询问:"你想保存什么?"
Step 3: 生成笔记
AI 自动处理: 1. 生成标题:从内容中提炼简洁的名词短语标题(中文或英文,跟随内容语言) 2. 生成摘要:一句话概括核心内容 3. 识别关键词:提取 2-3 个关键词,用于后续 tidy 分类参考
生成文件内容:
---
status: inbox
source: "AI conversation"
created: {YYYY-MM-DD}
keywords: [关键词1, 关键词2]
---
# {title}
{整理后的内容}
## 原始上下文
{如果是从对话提取的,保留关键上下文片段,方便日后回溯}文件路径:Inbox/{YYYY-MM-DD}-{title}.md
标题中的特殊字符(/\:*?"<>|)替换为 -。
Step 4: 写入文件
短内容(< 5 行):零确认直接写入。
长内容(>= 5 行):展示预览后写入:
预览:
标题: {title}
路径: Inbox/{filename}
摘要: {summary}
---
{前 200 字}...使用 Write 工具写入文件。
Step 5: 确认输出
✅ 已保存到: {vault_alias} → Inbox/{filename}
摘要: {summary}
💡 运行 /obos tidy 将 Inbox 中的笔记整理到正确目录/obos sync
扫描 vault,更新索引文件,输出健康报告,并为孤岛笔记建议链接。
Usage
/obos sync # 全量同步:更新 Index.md + CLAUDE.md + 健康报告 + 链接建议
/obos sync --status # 只读模式:仅输出健康报告
/obos sync --to work # 同步指定 vaultStep 1: 确定目标 Vault
使用 SKILL.md 中的 Vault Path Discovery 逻辑。
Step 2: 扫描 Vault
扫描标准目录(Inbox/、Notes/、Clippings/、References/、Categories/)中的所有 .md 文件。
对每个文件提取:
- 标题(文件名或第一个 H1)
- 首行摘要(跳过 frontmatter/标题,截取 60 字符)
- frontmatter
status字段(inbox/draft/refined) - frontmatter
review_needed字段(true/false) - 所有
[[wikilink]]引用(出链和目标) - 修改日期
构建链接图:内存中建立 笔记 → [出链] 和 笔记 → [入链] 的映射。
性能保护:vault 超过 500 个文件时,Recent Notes 只扫描最近 90 天。Categories 和统计始终覆盖全量。
Step 3: 更新 Index.md
--status 模式跳过此步。
写入 vault 根目录的 Index.md:
# Index
Last synced: {YYYY-MM-DD HH:MM}
## Recent Notes
| Note | Summary | Status | Dir | Updated |
|------|---------|--------|-----|---------|
| [[note]] | First line... | draft | Notes | 2026-01-27 |
(top 50 by modified date)
## Categories
- [[Category/Topic]] - {count} notes
## Statistics
- Total notes: {count}
- Inbox: {n} | Notes: {n} | Clippings: {n} | References: {n}
- Maturity: {n} inbox, {n} draft, {n} refinedStep 4: 更新 CLAUDE.md
--status 模式跳过此步。
边界保护:只修改 ## Current Context 段落,其他段落原样保留。
1. 读取 CLAUDE.md 2. 定位 ## Current Context(从标题到下一个 ## 或 EOF) 3. 替换(或追加)为:
## Current Context
Last synced: {date}
### Recent Activity
- {recent note 1}
- {recent note 2}
(up to 5 most recently modified notes)
### Active Topics
- {topic with most recent notes}
(up to 3 topics from Categories with most recent activity)Step 5: 健康报告
在所有模式下输出。
孤岛笔记
无入链的笔记(排除 Index.md、CLAUDE.md、Templates/、Inbox/ 中的文件)。
断链
指向不存在文件的 [[wikilink]]。
成熟度分布
各 status 的笔记数量。
待复核笔记
review_needed: true 的笔记数量与列表(最多显示 10 条)。
目录审计摘要
如果存在 /.obos/dir-audit.json,读取并输出目录动作摘要:
KEEP数量REORGANIZE数量ARCHIVE_DIR数量- 最近一次目录评估时间
输出格式:
Vault 健康报告
──────────────
总笔记: {count}
Inbox: {n} | Notes: {n} | Clippings: {n} | References: {n}
成熟度: {n} inbox, {n} draft, {n} refined
待复核: {n}
目录动作: {n} KEEP, {n} REORGANIZE, {n} ARCHIVE_DIR
孤岛笔记: {n}
断链: {n}
Last synced: {timestamp}Step 6: 链接建议(新增,合并原 link 功能)
--status 模式跳过此步。
对每个孤岛笔记(最多处理 10 个,按修改时间倒序):
1. 读取笔记内容,提取主题和关键词 2. 在 Index.md + vault 中搜索内容相关的笔记 3. 按相关度排序,建议 2-3 个链接
输出格式:
链接建议({n} 篇孤岛笔记):
- Notes/函数式编程.md
→ [[编程范式]], [[Haskell学习笔记]]
- Notes/GTD方法论.md
→ [[生产力工具]], [[时间管理]]如果有建议,用 AskUserQuestion 询问:
- "应用所有建议" — 批量添加到各笔记的
## Related段落 - "逐条选择" — 逐个笔记确认
- "跳过" — 不添加链接
/obos tidy
整理笔记并批量归位。默认增量执行,内置幂等保护,避免重复整理和重复重命名。
Usage
/obos tidy # 整理默认 vault
/obos tidy --to work # 整理指定 vault
/obos tidy --dry-run # 只预览不执行
/obos tidy --mode strong --priority structure --dry-run
/obos tidy --force-retidy
/obos tidy --force-renameParameters
| Param | Description |
|---|---|
--mode standard | 默认模式。仅整理 Inbox + vault 根目录散落文件 |
--mode strong | 强整理模式。先做目录必要性评估,再做文件迁移 |
--dry-run | 输出迁移方案,不做写入 |
--priority links | 链接优先(默认):优先避免断链 |
--priority structure | 结构优先:先完成归位,断链在后续报告修复 |
--project-policy contain | 默认。项目目录结构冻结:不改内部层级与文件名,只允许整体平移容器路径 |
--project-policy split | 覆盖策略。允许项目目录文件按语义打散到全局目录 |
--force-retidy | 仅本次忽略迁移锁,重新生成迁移决策 |
--force-rename | 仅本次忽略名称锁,允许再次自动重命名 |
Tidy State Files
tidy 使用 .obos 目录持久化状态:
/.obos/tidy-state.json:内容指纹、上次目标目录、名称锁等幂等状态/.obos/tidy-config.json:可选配置(含目录必要性评估参数)/.obos/dir-audit.json:目录评分、建议动作、执行动作、时间戳
tidy-config.json 示例:
{
"projectRootsExtra": [
"private/capitalistAnthropologyDiary"
],
"dirEvaluation": {
"enabled": true,
"protectedRoots": [".obsidian", ".obos", "Templates", "Attachments", "Excalidraw"],
"projectDecisionMode": "interactive",
"thresholds": { "keep": 70, "reorganize": 40 },
"archiveRoot": "_archive",
"deleteMarkdown": false,
"autoDeleteEmptyDirs": true
}
}Step 1: 确定目标 Vault
使用 SKILL.md 中的 Vault Path Discovery 逻辑。
Step 2: 安全检查(strong 模式必做)
当 --mode strong:
1. 检查 vault 是否为 git 仓库 2. 非 git 仓库时,提示先执行基线保护:
git initgit add -Agit commit -m "chore: vault baseline before obos tidy strong"
3. 若工作区有未提交变更,用 AskUserQuestion 询问:
- "继续并自动提交快照(推荐)"
- "继续但不提交"
- "取消"
Step 3: 加载幂等状态与配置
1. 读取 /.obos/tidy-state.json(不存在则初始化空状态) 2. 读取 /.obos/tidy-config.json(不存在则用默认配置) 3. 若状态文件损坏:强制切换为 --dry-run 并重建状态草案,不直接执行迁移 4. 初始化目录审计输出 /.obos/dir-audit.json
Step 4: 目录必要性评估(strong 模式先执行)
4.1 评估范围
- 评估 legacy 和业务目录必要性(例如
digital-hub/、private/、_drafts/、projects/) dirEvaluation.protectedRoots命中的强保护目录默认不参与清理迁移,仅记录评分并KEEP
4.2 评分规则(0-100)
按 6 个维度加权评分:
1. 结构角色(0-25):是否承担系统/模板/附件/项目容器职能 2. 内容活跃(0-20):近 90 天是否有修改 3. 内容密度(0-15):目录内文档数与非空率 4. 链接中心性(0-15):是否被大量 [[wikilink]] 引用 5. 冗余程度(0-15,反向):与其他目录职责是否重叠 6. 命名可理解性(0-10):目录名是否清晰表达用途
4.3 三档动作
>= 70→KEEP:保留目录,仅轻量规范化40-69→REORGANIZE:重组并迁移到更合理目录结构< 40→ARCHIVE_DIR:归档到_archive/YYYY-MM-DD/<old-path>/,迁移后删除空目录
4.4 项目目录交互决策(必须)
项目目录识别:
- 默认识别:
*/projects/* - 额外识别:
tidy-config.json.projectRootsExtra
当命中项目目录且 projectDecisionMode=interactive:
1. 输出决策卡片:评分、理由、预计迁移数、潜在断链数 2. 用 AskUserQuestion 逐目录询问:
- "保留"(KEEP)
- "冻结结构(推荐)"(保持项目内部结构不变)
- "允许拆散"(split)
3. 未经用户确认,不执行项目目录拆散
4.5 删除边界
- 默认
deleteMarkdown=false:不自动删除任何 markdown 文档 - “先归档后删除”针对目录结构与空目录,不删除笔记内容
- 若
autoDeleteEmptyDirs=true,迁移后自动删除空目录并写审计日志
4.6 评估输出
将每个目录写入 /.obos/dir-audit.json:
dirscorereasonssuggestedAction(KEEP/REORGANIZE/ARCHIVE_DIR)finalActiontimestamp
Step 5: 扫描待整理文件
扫描以下位置的 .md 文件:
standard 模式
1. Inbox/ 目录下所有文件 2. Vault 根目录下散落的 .md 文件(排除 CLAUDE.md、Index.md、README.md)
strong 模式
1. Inbox/ + vault 根目录散落 .md 2. REORGANIZE/ARCHIVE_DIR 目录下的 .md 3. 递归扫描时保留原相对路径,供迁移方案展示
排除项(不参与整理):
- 已在标准目录中的文件(Notes/、Clippings/、References/、Categories/、Templates/)
- Attachments/ 下的文件
.obsidian/下的文件- 所有 hidden / dot 目录(
./.*,如.agent/、.cursor/、.claude/) - frontmatter 中
status不是inbox且已在标准目录中的文件
如果没有待整理文件,输出提示并结束:
Inbox 为空,没有需要整理的文件。
运行 /obos save 收集新想法。Step 6: 双重幂等判定(核心)
每个候选文件按以下顺序判定:
1. Frontmatter 锁:已整理且无新变更时默认跳过 2. 状态指纹锁:比较 tidy-state.json 中的 lastContentHash + lastTargetDir + lastKnownName 3. 指纹一致且无 --force-retidy 时,跳过该文件(不重复整理) 4. 若检测到文件名被手工修改(与上次自动命名不同),自动写入 name_locked: true
Step 7: AI 分类
逐个读取文件内容,分析后判断目标目录:
| 目标目录 | 判断信号 |
|---|---|
Notes/ | 个人观点、独立概念、原创想法、方法论总结 |
Clippings/ | 外部内容摘录、网页剪藏、他人观点引用 |
References/ | 书摘、论文笔记、课程笔记、系统性参考资料 |
Categories/ | 主题索引、多篇笔记的汇总页 |
(原地保留) | 内容太短、置信度低或无法判断,标记为 review_needed: true |
分类依据优先级: 1. frontmatter 中的 keywords 或 source 字段 2. 文件内容语义分析 3. 文件名模式(如含日期、含 "clip-" 前缀等) 4. 原路径信号(如 clippings/、references/、projects/)
低置信度策略(默认):
- 不迁移,原地保留
- 标记
review_needed: true - 在方案与最终报告中列出
Step 8: 自动重命名策略(strong 模式默认开启)
命中文件名模式时,生成语义化新文件名:
未命名*.mdUntitled*.mddraft-*.md
重命名规则: 1. 优先使用首个 H1 2. 无 H1 时使用第一段核心句 3. 归一化非法字符并去重(冲突时追加 -2, -3) 4. 自动重命名默认只执行一次;后续命中 name_locked: true 时不再改名 5. --force-rename 仅对本次执行覆盖 name_locked 6. 在方案中显示 旧文件名 -> 新文件名
Step 9: 生成整理方案
输出方案表:
整理方案(共 N 个文件):
| # | 文件 | 当前位置 | → 目标 | 新文件名(可选) | 目录动作 | 项目边界 | 理由 |
|---|------|----------|--------|------------------|----------|----------|------|
| 1 | AI工具对比.md | Inbox/ | Clippings/ | - | REORGANIZE | n/a | 外部信息汇总 |
| 2 | 函数式编程思考.md | Inbox/ | Notes/ | - | REORGANIZE | n/a | 个人观点 |
| 3 | 未命名 1.md | projects/赤耘课/ | projects/赤耘课/notes/ | 财务会议总结.md | KEEP | contain | 项目内归位,不外抛 |
| 4 | 碎片想法.md | Inbox/ | (原地保留) | - | KEEP | n/a | 低置信度,待复核 |`--dry-run` 模式:输出方案表后结束,不执行任何操作。
Step 10: 用户确认
用 AskUserQuestion 询问:
- "全部执行" — 按方案批量移动
- "逐条确认" — 逐个文件询问是否移动
- "取消" — 不做任何操作
Step 11: 执行移动与目录动作
对每个确认的文件:
1. 如文件属于项目目录且 project-policy=contain:
- 目标路径必须仍在该项目目录内
- 不改项目内部目录结构
- 不改项目内文件名(除非显式覆盖)
2. 如有命名建议,先重命名再移动(或原地移动后重命名,二者效果一致) 3. 更新 frontmatter:
status:inbox→draft- 添加
moved_from: {原路径} - 添加
tidied: {YYYY-MM-DD} - 低置信度保留项:
review_needed: true - 检测到手工改名:
name_locked: true
4. --priority links:优先更新 [[wikilink]] 再落盘 5. --priority structure:先完成迁移,随后输出断链清单供批量修复 6. 对目录动作执行:
KEEP:仅记录,不迁移目录结构REORGANIZE:执行目录重组ARCHIVE_DIR:先归档目录结构再清理空目录
7. 持久化 tidy-state.json 与 dir-audit.json
Step 12: 输出结果 + 自动触发 sync
✅ 整理完成
目录评估:
KEEP: {n}
REORGANIZE: {n}
ARCHIVE_DIR: {n}
空目录清理: {n}
已移动:
Inbox/AI工具对比.md → Clippings/AI工具对比.md
Inbox/函数式编程思考.md → Notes/函数式编程思考.md
projects/赤耘课/未命名 1.md → projects/赤耘课/notes/财务会议总结.md
原地保留(待复核):
Inbox/碎片想法.md(review_needed: true)
目录审计已写入:
/.obos/dir-audit.json
正在更新索引...整理完成后自动执行 sync 逻辑(更新 Index.md + 健康报告),无需用户手动运行。
/obos vault
管理多个 Obsidian vault 的注册、切换和默认设置。
Usage
/obos vault add <alias> <path> # 注册 vault
/obos vault list # 列出所有已注册 vault
/obos vault default <alias> # 设置默认 vault
/obos vault remove <alias> # 移除注册配置文件
所有 vault 配置持久化到 ~/.proma/agent-workspaces/obsidian/obos-config.json。
结构:
{
"vaults": {
"personal": { "path": "D:/obsidian/personal", "default": true },
"work": { "path": "C:/Users/.../work-vault" }
},
"lastUsedVault": "personal"
}Step 1: 解析子命令
解析 /obos vault 后的第一个参数:add、list、default、remove。
无参数 → 等同于 list。
Step 2: 执行子命令
vault add
1. 验证 <path> 目录存在 2. 验证目录包含 .obsidian/ 子目录(如果不包含,警告但仍允许注册) 3. 读取 obos-config.json(不存在则创建空配置) 4. 写入新 vault 条目 5. 如果是第一个注册的 vault,自动设为 default 6. 输出确认:已注册 vault: <alias> → <path>
vault list
1. 读取 obos-config.json 2. 如果无配置或无 vault,提示用户先注册 3. 输出表格:
已注册 Vault:
| 别名 | 路径 | 默认 |
|------|------|------|
| personal | D:/obsidian/personal | ✓ |
| work | C:/Users/.../work-vault | |vault default
1. 验证 <alias> 已注册 2. 将所有 vault 的 default 设为 false 3. 将目标 vault 的 default 设为 true 4. 输出确认:默认 vault 已切换为: <alias>
vault remove
1. 验证 <alias> 已注册 2. 用 AskUserQuestion 确认删除:"确认移除 vault 注册 '<alias>'?(不会删除实际文件)" 3. 从配置中移除 4. 如果移除的是 default vault 且还有其他 vault,提示用户设置新的 default 5. 输出确认:已移除 vault 注册: <alias>
错误处理
- alias 重复 → 提示已存在,询问是否覆盖
- path 不存在 → 报错,不注册
- 配置文件损坏 → 备份后重建空配置