その「Obsidian×AI」、Obsidianは何もしていない
Obsidian に AI を組み合わせて「第二の脳」を作る、というやり方が広まっています。Vault を Cursor や Claude Code に読ませて、蓄積したノートを検索させる構成です。
自分の環境でこれがほとんど機能していなかったので、原因を測りました。結論から書くと、Obsidian が持っている全文索引は Electron のプロセスの中に閉じていて、外の AI ツールからは1バイトも使えません。AI がやっているのは、素の Markdown を grep することだけです。
つまり「Obsidian を使っているから AI の検索が速い」という因果は成立しません。AI 側で効いていたのは索引ではなく、フロントマターやリンクといったプレーンテキストの規約のほうでした。
先に断っておくと、Obsidian は良いアプリです。書いたものが互いに繋がり、検索は一瞬で返る。その評価を否定する記事ではありません。測ったのは「AI と組み合わせたとき、その速さが AI 側にも効いているのか」という一点だけです。
測った手順と、そこから出てきたもう1つの発見も記録します。ノートが古びるかどうかは、書き手の几帳面さではなく、書き戻すルールがあるかどうかで決まる、という話です。
きっかけ
手元の Vault には141枚のノートがありました。調べた時点で、直近3か月に触られていたのは2枚だけです。
蓄積は増えているのに、参照されていない。まずここを疑うべきでした。
find "$VAULT" -name '*.md' | wc -l # 141
find "$VAULT" -name '*.md' -mtime -90 | wc -l # 2
Obsidian は本当に索引を持っている
Vault の中を見ても、あるのは素の Markdown と .obsidian/ 配下の設定 JSON だけです。DB はありません。
索引はアプリ側にあります。
du -sh ~/Library/Application\ Support/obsidian/IndexedDB/*
2.4M app_obsidian.md_0.indexeddb.blob
245M app_obsidian.md_0.indexeddb.leveldb
245MB。中身を覗くと、ノートの本文がまるごと入っています。
strings ~/Library/Application\ Support/obsidian/IndexedDB/*.leveldb/*.ldb | head
path"!notes/example.md"
data
0j0D0_0
0n00ckW0D
path と data の対になっています。日本語が化けているのは UTF-16 で格納されているためで、strings が1バイトずつ拾って壊しているだけです。
さらに、開いたことのある Vault が全部混ざっています。登録済み Vault の一覧は次のファイルにあります。
cat ~/Library/Application\ Support/obsidian/obsidian.json
{ "vaults": { "188f32e3fc96d54e": { "path": "/path/to/vault", "ts": 1785114741427, "open": true } } }
Obsidian の全文検索が一瞬で返るのも、グラフビューが描けるのも、バックリンクが即座に出るのも、この索引があるからです。ここまでは想像どおりでした。
なぜ外の AI ツールから使えないのか
これは Chromium の IndexedDB です。Obsidian が Electron 製なので、ブラウザのストレージがそのままアプリのストレージになっています。
外から使えない理由は3つあります。
・LevelDB はプロセス内から開く前提の組み込みストレージで、ネットワーク越しのクエリ口を持たない。サーバーではないので、接続して SQL を投げる相手がいない
・Obsidian の起動中はロックがかかる。別プロセスから同じディレクトリを開こうとすると弾かれる
・仮に読めても、キーの構造は Obsidian の内部実装であって公開スキーマではない。バージョンが上がれば黙って変わる
一方、Cursor や Claude Code がファイルを探すときにやっているのは ripgrep 相当の全文検索です。対象は .md ファイルそのもので、索引には触れません。
つまり Obsidian がインストールされていようがいまいが、AI から見える景色は同じです。Markdown が並んだフォルダがあるだけです。
では AI 側で何が効いていたのか
索引ではなく、索引を育てるために書き手が守っている規約のほうでした。
・フロントマターで属性を持たせる
・[[wikilink]] で関連を張る
・1ファイル1トピックにする
・ファイル名を検索語にする
これらは全部プレーンテキストです。だから grep で届き、AI がそのまま読めます。
言い方を変えると、規約はどのツールにも持ち運べますが、索引はどこにも運べません。Obsidian をやめても規約だけは資産として残ります。
もう1つの発見: 古びるかどうかはルールの有無で決まる
調べているうちに、同じ Vault の中で状態が正反対のファイルが2つ見つかりました。
・前日に更新されていた表
・8か月前から止まっていた一覧
前者は全プロジェクト共通のポート割り当て表で、AI への指示書(CLAUDE.md)に「番号を取ったら、使い始める前に表へ追記する」と書いてありました。後者はパッケージの一覧で、対応する指示がどこにもありませんでした。
凍結していたほうは5件を提示し続けていましたが、実際にはそのとき16件に増えていました。そして一度も「私はもう古い」とは言いません。開けば堂々と5件を返します。
同じアプリ、同じフォルダ、同じファイル形式です。違いは書き戻す経路があるかどうかだけでした。
ここが実務的には一番効きます。AI に読ませる知識を用意するとき、置き場所を選ぶより先に決めるべきなのは、それを誰がいつ書き戻すかです。書き戻す経路の無いドキュメントは、置き場所がどこであれ必ず腐ります。
自分の環境で確かめる
そのまま叩けるコマンドをまとめておきます。
-mtime -90 を使うのは、-newermt '3 months ago' のような相対表現が macOS では通らないためです。GNU find なら解釈しますが、BSD find や bfs は弾きます。日付で切りたいなら date -v-3m +%Y-%m-%d の出力を -newermt に渡してください。
# 索引の大きさ
du -sh ~/Library/Application\ Support/obsidian/IndexedDB/*
# 登録済み Vault の一覧
python3 -c "import json,os;print(json.load(open(os.path.expanduser('~/Library/Application Support/obsidian/obsidian.json')))['vaults'])"
# アプリ本体の大きさ
du -sh /Applications/Obsidian.app
# いま起動しているか
pgrep -x Obsidian && echo running || echo not running
私の環境では、440MB のアプリと245MB の索引が、起動されないままディスクに置かれていました。
まとめ
・Obsidian は245MB の全文索引を持っている。ただし Chromium の IndexedDB で、Electron のプロセス内に閉じている
・Cursor や Claude Code はその索引を一切使わない。素の Markdown を grep しているだけ
・「Obsidian と組み合わせると AI の検索が速い」という因果は成立しない
・AI 側で効いているのはフロントマター、リンク、1ファイル1トピックといったプレーンテキストの規約。これらはツールを乗り換えても残る
・ノートが古びるかどうかは置き場所ではなく、書き戻すルールの有無で決まる。同じ Vault の中に、ルールのある表とルールの無い一覧が、生と死で並んでいた
・AI に知識を読ませる構成を作るなら、索引を持つアプリを選ぶことより、書き戻す経路を先に設計するほうが効く