Claude Code / Desktop の記憶 OSS「KIOKU」を同日に 2 リリース (v0.5.0 + v0.5.1、2026-04-23) 出したので、機能面と設計判断をまとめます。
1 行でまとめると:
- v0.5.0: 外部ドキュメント (PDF / Markdown / EPUB / DOCX) の統一 ingest router
- v0.5.1: session 間の短期記憶を繋ぐ hot cache + PostCompact hook
「外部の知識を取り込む (ingest) → session 間で持続させる (persist)」という連続した一対のリリースです。
前提
KIOKUを初めて見る方向けにご紹介します。
Claude Code は過去のセッションで得た知識をどんどん忘れます。KIOKU はあなたが Claude と話した記憶を自動で Wiki に蓄積し、次のセッションで呼び戻せるようにする OSS です。Obsidian Vault 上に構造化されたナレッジベース (Andrej Karpathy の LLM Wiki パターン がベース) を作って、Git で複数マシン間同期します。
v0.5.0: PDF / MD / EPUB / DOCX の統一 ingest router
変更点
v0.5.0 までは PDF 用・Markdown 用・URL 用で別々の MCP tool が並んでいました。v0.5.0 で kioku_ingest_document(path) という 1 本の入り口を切って、拡張子で dispatch する形にリファクタしました。
kioku_ingest_document("論文.pdf") → PDF handler
kioku_ingest_document("note.md") → PDF と同じ extractor (plain text chunk)
kioku_ingest_document("book.epub") → EPUB handler (新規、yauzl ベース)
kioku_ingest_document("spec.docx") → DOCX handler (新規、mammoth ベース)
旧 kioku_ingest_pdf は deprecation alias として v0.5 〜 v0.7 window で残存、v0.8 で削除予定です。新規統合は kioku_ingest_document を使ってください。
使い方 (Claude Desktop / Code から)
# 1. raw-sources/ 配下にファイルを置く
cp 論文.pdf $OBSIDIAN_VAULT/raw-sources/papers/
cp book.epub $OBSIDIAN_VAULT/raw-sources/books/
cp spec.docx $OBSIDIAN_VAULT/raw-sources/specs/
# 2. Claude に頼む
kioku_ingest_document("raw-sources/papers/論文.pdf") で要約して
kioku_ingest_document("raw-sources/books/book.epub") で取り込んで
cron 経由の自動取り込み (auto-ingest.sh) も同じ router を通ります。vault の raw-sources/ 配下を 1 日 3 回スキャンして、未処理のドキュメントを wiki/summaries/ に要約していきます。
EPUB 取り込みの設計: 8 層防御の ZIP 展開
EPUB は実体が ZIP なので、攻撃者ペイロードの典型的な流入経路です。KIOKU では Readability に食わせる前に 8 層の防御を直列に置いています:
| 層 | 防ぐもの |
|---|---|
| 1 | zip-slip (../ を含む entry path) |
| 2 | symlink entry (vault 外を指すリンク) |
| 3 | 累積 size cap (爆弾 EPUB、展開後 500 MB まで) |
| 4 | entry count cap (10,000 エントリまで) |
| 5 | NFKC filename 正規化 (Unicode normalization attack 対策) |
| 6 | nested ZIP skip |
| 7 | XHTML に対する XXE pre-scan (<!DOCTYPE 拒否) |
| 8 | XHTML 内 <script> / on*= sanitize |
全層を通過した XHTML だけ Readability + Turndown で Markdown 化、spine 順で .cache/extracted/epub-<subdir>--<stem>-ch<NNN>.md に保存します。2 章以上の EPUB は目次 -index.md も自動生成、後段の auto-ingest cron が LLM 要約時に参照します。
DOCX 取り込みの設計: mammoth + yauzl の二段構え
DOCX は ZIP + XML。mammoth が内部で使う jszip は XXE / zip-slip に無防備なので、yauzl で先に ZIP を開いて 8 層防御を通過させる構造にしました:
- yauzl で ZIP を開き、8 層防御 (EPUB と共通) を通す
-
word/document.xml/docProps/core.xmlにassertNoDoctype()で XXE pre-scan - 全通過したら ZIP を閉じて mammoth に Buffer を渡す
- Metadata は
--- DOCX METADATA ---fence で囲って untrusted 注釈付きで保存
画像 (VULN-D004/D007) と OLE 埋め込み (VULN-D006) は MVP では skip しています。画像対応は EPUB と同じ pattern で将来拡張予定。OLE は threat surface が広いため別 PR で詰めます。
Unicode ファイル名対応
EPUB / DOCX extractor は cron (auto-ingest.sh) から argv でファイル名を受け取るので、raw-sources/<subdir>/<stem>.<ext> を分解する正規表現が必要です。ASCII 前提の \w では日本語・中国語のファイル名を拾えないので、Unicode プロパティ escapes を使いました。
const m = argv[2].match(/raw-sources\/([\p{L}\p{N}_-]+)\/([\p{L}\p{N}_-]+)\.(epub|docx)$/u);
// ^^^^^^^^^^^^^^^^^ ^^^^^^^^^^^^^^^^^ ^
// Unicode-aware Unicode-aware unicode flag
\p{L} は任意のスクリプトの文字 (Latin / Cyrillic / CJK / Arabic / Devanagari など)、\p{N} は数字、/u flag が必須。これで 論文.epub や 日本語メモ.docx も cron 経路で正しく拾えます。
v0.5.1: hot cache で session 跨ぎ context を維持
変更点
Claude Code は長い session で context compaction (要約圧縮) が走ると、直前までの作業記憶が大幅に減ります。v0.5.1 では wiki/hot.md という 1 ファイルに「短期記憶」を蓄積し、SessionStart と PostCompact (新 hook event) の両方で注入 する仕組みを入れました。
hot.md のフォーマット
---
type: hot-cache
updated: 2026-04-23
---
## Recent Context
- いま何を作っているか
- 直前の session で決めた設計判断
- 次の session で覚えておきたいコンテキスト
500 word soft limit、hard cap 4000 文字。LLM が session 終わりに書き換える前提の軽量メモです。
注入戦略
| Event | 注入内容 | 理由 |
|---|---|---|
| SessionStart | hot.md + index.md の両方 | session 冒頭は全 context が必要 |
| PostCompact (新) | hot.md のみ | index.md は context に残存、token 節約 |
Stop hook の opt-in prompt
「session 終わりに hot.md を書き換える」提案を Stop hook で出すかどうかは、default opt-out にしました。明示的に KIOKU_HOT_AUTO_PROMPT=1 を set したときだけ提案 prompt が出ます。
# 明示的に opt-in する場合のみ
export KIOKU_HOT_AUTO_PROMPT=1
理由: session-logs/ は .gitignore 対象でローカル保持ですが、hot.md は Git sync 対象。書き換え内容がそのまま GitHub private repo に commit されるため、マスクされるはずの API key が紛れ込む経路を予防する必要があります。security boundary が違うものを同じ自動化で扱わない、という境界設計です。
Security boundary
- hot.md 注入前に
applyMasks()適用 (API key / token パターン伏字化、既存mcp/lib/masking.mjsを共有) -
scan-secrets.shの scan 対象にwiki/hot.mdを追加 -
realpathで symlink escape (vault 外パス参照) を拒否 - 4000 文字超過は truncate + WARN log
インストール (新規ユーザー向け)
クイックインストール (Claude Code Max プラン)
# 1. Vault を作成 (Obsidian で新規 Vault、path を OBSIDIAN_VAULT に export)
export OBSIDIAN_VAULT="$HOME/claude-brain/main-claude-brain"
# 2. GitHub private リポジトリを作成して Vault を git init + push
cd "$OBSIDIAN_VAULT"
git init && gh repo create --private --source=. --push
# 3. KIOKU を clone して setup
git clone https://github.com/megaphone-tokyo/kioku.git ~/kioku
cd ~/kioku
bash scripts/setup-vault.sh # Vault 初期化
bash scripts/install-hooks.sh --apply # Claude Code Hook を ~/.claude/settings.json にマージ
# 4. 定期実行 (自動 ingest + lint) を登録
bash scripts/install-schedule.sh # macOS LaunchAgent / Linux cron を自動判別
# 5. qmd 検索 (任意、Wiki 全文検索)
bash scripts/setup-qmd.sh
bash scripts/install-qmd-daemon.sh
# 6. kioku-wiki MCP サーバー (Claude Desktop 経由で wiki 操作)
bash scripts/setup-mcp.sh
bash scripts/install-mcp-client.sh --apply
Claude Desktop 向け: .mcpb ドラッグインストール
-
Releases から最新の
kioku-wiki-0.5.1.mcpb(9.2 MB) をダウンロード - Claude Desktop を起動、設定 → Extensions / Connectors 画面に
.mcpbをドラッグ - インストールダイアログで Vault directory を picker から選択 → Install
- 新しいチャットを開いて
kioku_read で wiki/index.md を読んでで動作確認
エンドユーザー側で Node のインストールは不要 — バンドルに @modelcontextprotocol/sdk が同梱され、Desktop 内蔵の Node ランタイムで動きます。
設計判断: defuddle を作らなかった話
v0.5.2 で defuddle (web 広告 / boilerplate 除去で token 40-60% 削減) を作る予定でしたが、着手前の 実測 probe で不要判定、skip しました。
測ったこと
-
raw-sources/articles/の既存 10 件の body 長: 全件 substantial (1,640 〜 170,204 bytes、中央値 ~10KB) -
session-logs/38 件 grep (short-content/readability.*fail/extracted.*empty): 0 件 -
.cache/extracted/url-*失敗 cache: 0 件
既に使っている @mozilla/readability が広告 / boilerplate を十分除去していて、defuddle の前段を足す理由が測定データに存在しない、という結論。工数 6-10h を v0.6.0 Phase C (LP β + plugin marketplace) に振り分けました。
判断は再燃条件付きで handoff/open-issues.md §19 に記録してあります (Readability が空に近い抽出を生成する事例発生 / JavaScript-heavy SPA の本文抽出失敗 / 競合が defuddle で UX 優位を示した時、のいずれかで再評価)。
テスト / Lint
- v0.5.0: Bash 158 assertions + Node 全 suite green (
npm auditで runtime deps 0 vulnerabilities、red-hacker + blue-hacker 並列/security-reviewで HIGH/CRITICAL 0) - v0.5.1: Node 47 件 (HOT-1..9d + HOT-V1/V2 + injector H1-H5) + Bash 488 assertions (IH-PC1/2 + SS-H1 + CGP-2 拡張) 全 green
- 既知 issue:
fast-xml-parserCVE-2026-41650 は XMLBuilder 固有の問題、KIOKU は XMLParser (読み込み側) しか使わないので exploit 不可。dependabot alert 解消のため v0.5.1 で^5.7.0に upgrade 済
Release 情報
-
v0.5.0 Release Notes —
kioku-wiki-0.5.0.mcpb -
v0.5.1 Release Notes —
kioku-wiki-0.5.1.mcpb
v0.6 に向けて
v0.5 系で ingest → persist の基盤が揃ったので、次の Phase C では 外部 user を迎え入れるフェーズに入ります:
- Agent Skills cross-platform 対応: Cursor / Windsurf / Gemini CLI / Codex に symlink で広げる
-
Claude Code plugin marketplace 登録:
claude plugin install kioku@megaphone-tokyoで 1 行 install -
Delta tracking:
.raw/.manifest.jsonで source-level hash 管理 (同 PDF 2 回 ingest で skip) -
Obsidian Bases dashboard:
wiki/meta/dashboard.baseで ingest 履歴 / orphan 一覧を動的表示 - LP β + Discord soft launch: 1 人 dogfooding から外部 feedback を受け取る体制へ
まとめ
-
v0.5.0: PDF / MD / EPUB / DOCX の統一 ingest router (
kioku_ingest_document)、EPUB 8 層防御、DOCX の mammoth + yauzl 二段構え -
v0.5.1: hot cache (
wiki/hot.md) + PostCompact hook、Stop hook は default opt-out (security boundary が違うため) - v0.5.1 release 当日の 4 回 iteration: Claude Code v2 の per-event hook schema drift に合わせて schema 対応 (全て v0.5.1 タグ前に commit)
- v0.5.2 defuddle は skip: 実測データで不要判定、再燃条件付き
- MIT License、フィードバック歓迎です
他のプロダクト
こんにちは、季節より。 / hello from the seasons.
季節の写真を集めたギャラリーサイトです。作者が撮影した四季折々の写真を眺められるだけでなく、自分の画像と季節の写真を AI で合成する機能もあります。写真が好きで、AI で遊ぶのも好き、という個人的な興味から作りました。
作者: @megaphone_tokyo
コードと AI で何かつくる人 / フリーランスエンジニア 10 年目 / 東京
