BLOG.HIRO UENO.ART
← index
2026.01.21

分けたはずが混ざる — システムプロンプトを1つに戻す

MONET(オーケストレーター)のシステムプロンプト(AIに最初に渡す指示文、以降SP)は、3つのファイルに分けて持っていた。書き手が違うから分ける。理屈としては綺麗に分かれてる・・・と思ってた。

分けたはずのものが、あちこちで混ざってきた。


3つのファイルはこう。

system_prompt_persona.txt  ← MONETの人格・口調。僕が書く
system_prompt_core.txt     ← 僕の恒久的な情報(プロジェクトとか価値観とか)。僕が手で足す
context_summary.txt        ← 直近の状況。Librarianが毎朝4時に自動生成する

分けた理由は、書き手が違うから。人格と恒久情報は僕。直近の状況は Librarian(前の記事で書いたメモリ管理アプリ)。触る頻度も違う。人格はめったに変わらないし、Core も昇格した内容を足す時だけ。Context は毎日書き換わる。

書き手と頻度が違うなら、ファイルも分けておく。各ファイルが自分の役割を持ってる。当時はこれで整理できていると思っていた。


でも実際それで運用してみると扱いづらかった。

まず、3つが別々に育っていく。Persona に書いたことと Core に書いたことが似てきたり、Context の内容が Core と微妙に食い違ったり。ファイルを3つ開いて見比べないと、MONET が全体として何を読んでいるのかわからない。

次に、Librarian が取ってくるメモリの層。前の記事で書いた通り、Librarian は最新100件のうち25件を「人物像」、75件を「最近の会話」として取ってくる。この「人物像」の25件が、Core に書いてあることとほぼ同じだった。僕の価値観、判断基準、変わらない事実。Core に手で書いたものと、Librarian が毎朝メモリから拾ってくるものが、同じことを2回言ってる。

前の記事で、重複してもそんなに困らない、と書いたばかりだった。あれはサマリーの中で数行かぶる話。今回は取ってくる層そのものが、Core と同じことをもう一回言うための層になっていた。層ごと廃止した。


一番気持ち悪かったのは3つ目。

Librarian が生成した Context を読んだら、去年12月の週間サマリーが「直近の状況」として載っていた。1ヶ月前の話が、今の話として MONET に毎朝渡っていた。

コーディングしてくれている Claude Code(以降 Code)に見てもらったら、原因はインポートの日付。古いメモリを別のシステムから移した時に、作成日がインポートした日になっていた。Librarian は「直近30日・100件」の条件でメモリを取りに行くので、中身は12月でも作成日が今月なら「直近」に引っかかる。

対策は取得範囲を絞っただけ。30日100件を、7日10件に。目の前の混入は止まったけど、根本は何も直ってない。日付が化けたデータはそのまま残ってるし、取ってくるロジックも変えてない。

Librarian が書いたものを、毎朝そのまま MONET に渡していた。読み返しもせずに。司書に棚を任せて、棚に何が並んだか見てなかった。


3つとも同じ形をしてる。分けて置いたはずのものが、別の場所で混ざって出てくる。

ファイルを分けても、中身は分かれてくれない。 そういうことだと思う。


で、Code に頼んで1つにまとめてもらった。

system_prompt.txt
├── PERSONA  MONETの人格・口調
├── CORE     僕の恒久的な情報
├── CONTEXT  直近の状況(Librarianが更新)
└── RULES    ツール使用ルール

1ファイルの中をセクションで区切る。区切りは HTML コメントのマーカーで、Librarian は CONTEXT のセクションだけを見つけて書き換える。設定ページはタブ切り替えにして、CONTEXT には読み取り専用のバッジをつけた。僕が間違えて手で触らないように。

分けるのをやめた代わりに、中で決めたことがある。どのセクションを誰が書くか。

セクション 書く人
PERSONA
CORE
CONTEXT Librarian
RULES

MONET 本人は読むだけ。自分の SP を書き換える権限は、当面渡さない。

あと、保存のたびにバックアップを残すようにした。SP が壊れると、MONET は自分が誰かわからない状態で起動しかねない。Librarian が毎朝自動で書き込むファイルなので、いつでも前の版に戻せるようにしておきたかった。


変更としては小さい。3つのファイルを1つにして、タブをつけて、書く人を決めた。それだけ。

でも、ファイルを3つ開いて見比べる作業がなくなった。MONET が何を読んでいるかは、1つのファイルを上から読めばわかる。

Librarian 周りは、とりあえず動いてる状態のまま。CONTEXT には古い情報がまだ混ざってて、これは手で直す。取得ロジックの見直しも残ってる。分けるのをやめただけで、混ざったものの掃除はこれから。