「毎回、最後に変なメッセージが出るんですけど」。運用中のAIエージェントについて、そんな報告が上がることがあります。エラー画面は出ません。業務も終わっています。ただ、完了報告のはずの場所に、身に覚えのないファイル名が並んでいる。
調べた担当は「ログを見ましたが、ルールどおりに動いています。壊れていません」と答えました。それでも症状は消えません。
この記事は、そのときWEBMARKSで何が起きていたかを、症状・誤診・真因・恒久対策の4段で追います。犯人にされていたのは、ファイルの更新時刻でした。
本記事の検証環境:Codex(別のAIエンジン)/Claude Codeと並行稼働するMac/2026-07-08〜2026-07-10の社内記録。
こんなふうに調べていませんか
- AIエージェントの動きがおかしいのに、ログを見ても「正常」としか出てこない
- 調査担当の「壊れていません」を、どう検証すればいいか分からない
- 複数のAI社員が同じ場所を触っていて、どの成果物が誰のものか言えない
この記事を読み終えたときに手に入るもの
- 「壊れていない」という結論を、実物と突き合わせて確かめられるようになります
- 更新時刻に頼った判定がどこで崩れるかを、自分の環境で説明できるようになります
- 次に同じ症状が出たときの確認順序が、4段の形で手元に残ります
結論30秒でわかる、この記事の結論
- 原因切り分けでは、更新時刻を「誰が作ったか」の証拠に使わないでください。
- 誤診は、ログの文面と利用者の画面を突き合わせない段階で生まれます。
- 直す対象は、検知の条件ではなく、持ち主を記録する方式のほうです。
進行役は3人です。若葉さん(Web担当2年目)がそもそもを聞き、高梨課長が自分の手で直す側を、鈴木さん(本誌監修)が答える側を担当します。
01AI社員の運用で障害が出たとき、原因切り分けは何から始めるんですか?
若葉さん「なんか変です」くらいしか言えない報告でも、障害報告になるんでしょうか。
鈴木さんなりますよ。最初はそれで十分です。大事なのは、その体感を打ち消さずに、見えたものをそのまま書き留めることなんです。
WEBMARKSは2026-07-08、Codex(別のAIエンジン)に、成果物が納品先へ正しく格上げされたかを末尾で確認する仕組みを入れました。直後から、業務と無関係な確認メッセージが毎回出るようになりました。
TASK-048というブラッシュアップ監査を45分かけて実行した回では、完了報告のはずの末尾が「【格上げ確認ゲート】直近で成果物が作られました」という表示に乗っ取られました。列挙されたのは、その回のセッションが一度も触っていない別案件のファイルです。
この確認メッセージは、導入からの3日間で233回発火しました(出典: 社内タスク台帳、2026-07-10記録)。
| 項目 | 記録に残っている内容 |
|---|---|
| 発火回数 | 3日間で233回 |
| 症状 | 完了報告の末尾が、そのセッションが触っていない別案件のファイル列挙に置き換わる |
| 判定材料 | ファイルの更新時刻(mtime)から担当セッションを推定していた |
| 解消 | thread・case・ハッシュを明示記録する方式へ全面刷新して収束 |
記録として足りなかったものも書いておきます。日ごとの内訳を残していません。合計だけを数えていたため、初日が何度で、パッチを当てた後に何度へ減ったのかを言えなくなりました。合計は規模を示しますが、収まりつつあるのかは読めません。障害の記録は、規模と推移の両方があってはじめて次の判断に使えます。
体感のほうは正確でした。「毎回最後に変なメッセージが出る」「Codexが動いていない気がする」という言い方は、症状の記述として十分に具体的です。曖昧なのは言葉づかいで、観察ではありません。
やっかいなのは、業務の完了報告そのものが上書きされる点です。次に何を確認すればいいか分からないまま、無関係な情報だけが残ります。AI社員を並行で動かす現場では、これが「どれが自分の成果物か言えない」に直結します。
この章のまとめ
最初にやるのは、原因の推定ではありません。見えた症状と、記録に残っている数字と、残っていない数字を分けて書き出すことです。
02AIエージェントが「壊れていません」と答えた原因切り分けは、なぜ誤診だったんですか?
高梨課長ログを確認して「正常です」と返ってきたら、うちはそこで調査を終えます。それだと足りないんでしょうか。
鈴木さん足りない場合があります。ログの文面が正しく見えることと、利用者の画面が正しいことは、別々に確かめる必要があるんです。
最初にこの症状を調べた担当は、セッションログの最後の1行だけを読み、「既存の運用ルールどおりに動いている、壊れていない」と結論づけました。これが誤診でした。
根拠になったのは、確認メッセージの文面が既存ルールの体裁に沿っていたことだけです。利用者が画面で見ていたもの、つまり無関係な別案件のファイル一覧とは突き合わせていません。
原因切り分けでもっとも危険なのは、この「文面は正しそうに見える」段階で止まることです。ポストモーテムの実務書は、対応者を個人として断罪しない姿勢を説きます。同時に、システムの脆弱性そのものを特定することへ焦点を当てるべきだとも述べています(出典: Google SRE Book「Postmortem Culture」)。
今回でいえば、脆弱性は担当者の注意力ではありません。検証手順に「実物の画面と照合する」工程が入っていなかったこと。そこが脆弱性です。
| 論点 | 誤診(最初の結論) | 真因(実際の原因) |
|---|---|---|
| 何が起きているか | ルールどおりの正常な確認表示 | 旧フックの誤爆 |
| 判断の根拠 | セッションログの最終メッセージのみ | 更新時刻で別セッションの成果物を自分のものとみなす設計 |
| 突き合わせた対象 | ログの文面だけ | 利用者が見た画面とは未照合 |
| 結果 | 「壊れていない」と回答 | 3日で233回の誤爆が継続 |
体感が正しく、結論が誤っている。この食い違いはくり返し起こります。とくにAIエージェントは出力が人の読む文章なので、「それらしく読める」という理由で通過しやすくなります。
この章のまとめ
「壊れていない」と結論する前に、突き合わせた相手を1つ挙げてください。挙がらないなら、切り分けはまだ済んでいません。
03更新時刻で持ち主を決めると、AI社員の運用障害の原因切り分けはどこで狂うんですか?
若葉さんそもそも更新時刻って、何が書いてある値なんですか。
鈴木さん「いつ変わったか」だけです。「誰が変えたか」は書いていません。1人で使う机なら、動いた時刻から触った人を当てられますよね。同じ机を何人かで同時に使い始めると、その当て方が効かなくなるんです。
真因は、旧フック(承認ゲート用の確認スクリプトの旧版)の設計そのものにありました。
Codexには、セッションを一意に識別するIDがありません。その代わりに「前回の確認以降に更新時刻が動いたVault内ファイルは、このセッションの成果物」とみなす作りにしていました。
このMac上では、画像生成バッチやClaude Codeの並行セッションが常時動いています。更新時刻はファイルシステム全体で共有される値なので、複数の処理が同時に走る環境では「誰が触ったか」の手がかりになりません。
同じ問題は分散システムの世界でも古くから知られています。W3C Trace Context仕様は、高スループット環境では同時刻に複数のリクエストが発生し、タイムスタンプ単独では識別できないと明記しています。だからこそランダム生成した明示的なtrace-idを識別の起点に据えます(出典: W3C Trace Context仕様)。旧フックは、この教科書的な落とし穴を踏んでいました。
ログだけでは追跡に足りない、という指摘も一致します。分散トレーシングの解説では、ログだけでは実行経路を追うのに文脈情報が不足しがちで、根本原因分析にはリクエスト単位の明示的なつながりが要ると説明されています(出典: OpenTelemetry Observability Primer)。旧フックが持っていたのは間接的な手がかりだけで、どのセッションが何を書いたかというつながりはどこにもありませんでした。
自分の環境で見分けるときの問いは1つです。「その判定は、書き込んだ本人が残した記録を見ていますか。それとも、外から観察した値を見ていますか」。後者なら、並行して動くものが増えた時点で崩れます。
04生成AIのエンジンを乗り換えると、原因切り分けの前提はどこが崩れるんですか?
同じ機能をClaude Code側からCodex側へ移したとき、作業の単位を識別するIDがあるという前提が崩れていました。
移植で落ちるのは、たいていコードではありません。コードは動きます。落ちるのは、暗黙に当てにしていた前提です。今回は「セッションを識別できる」が消え、その穴を更新時刻で埋めたところから誤爆が始まりました。
やっかいなのは、前提が消えたことが動作に出ない点です。フックは起動し、メッセージも出ます。壊れて見えないまま、判定の精度だけが落ちます。だから乗り換えのときは、機能の一覧ではなく前提の一覧を先に並べてください。
05パッチを当てても再発するとき、AIエージェントの原因切り分けは何を疑うんですか?
2026-07-09、中間ファイルを除外するパッチを当てました。それでも再発しました。
除外を足す直し方は、症状の側から後追いする形です。誤爆したファイルの種類を1つ消せば、その種類では出なくなります。ただ判定の方式は変わらないので、次の種類でまた出ます。いわゆるモグラ叩きです。
見分け方は1つです。「今回の修正で、どの条件のときに誤爆しなくなるか」を1文で言えるかどうか。「このファイルは除外したので出ません」としか言えないなら、方式ではなく症状を直しています。
この章のまとめ
同じ症状の再発は、直し方の階層が合っていない合図です。条件を足す手を止め、判定の土台にある考え方を疑ってください。
06AI導入を進めた現場で、書き込みの証跡はどう残せばいいんですか?
高梨課長記録を足すと、現場の手数は増えませんか。毎回IDを書くようだと続きません。
鈴木さん人は書きません。書き込みの直後に、機械が勝手に残す形にします。手で書く運用は、忙しい日から先に抜けていきますから。
2026-07-10、WEBMARKSはこの仕組みを全面的に作り直しました。柱は、更新時刻による推測をやめ、書き込みイベントを明示的に記録する方式へ替えたことです。
- 更新時刻の走査・時間窓・クールダウンといった間接推測の仕組みをすべて廃止する
- ツール実行の直後に発火するフック(
record-output.py)が、そのスレッドが実際にWrite・Edit・ApplyPatchしたファイルだけを、スレッドID・案件ID・SHA-256ハッシュ付きで記録する - セッション終了時のゲート(
promotion-gate.py)は、この記録だけを見て判断する。他セッションの成果物が混ざる経路自体が無くなる
記録先のディレクトリ名は、スレッドIDと案件IDを連結した文字列のSHA-256ハッシュです。案件をまたいだ混線も構造的に防いでいます。
判定の性質も変わりました。以前は「動いたものの中から、自分のものらしいものを選ぶ」。いまは「自分が書いたと名乗った記録だけを見る」です。選ぶ作業が消えたぶん、選び方の失敗も消えます。
フックが判断をJSON形式で返し、必要な処理だけを止める設計は珍しくありません。WEBMARKSはClaude Code側でも同じ仕組みを採用しています(出典: Claude Code公式フックドキュメント)。エンジンが変わっても骨格は使い回せます。
07検知の仕組みが誤作動したら、AIエージェントは止める側と通す側のどちらへ倒すんですか?
高梨課長検知が外れたときは、止めるのが安全だと思っていました。違うんですか。
鈴木さん何を守りたいかによります。今回は、止めると正常な成果物まで巻き込んで業務が止まる。だから通す方向へ倒しました。ただし通した記録は残します。
検証に失敗したとき、書き込み記録そのものが見当たらない場合も含めて、ブロックではなく通過を選ぶ設計にしました。止める方向に倒すと、正常な成果物まで巻き込んで業務が止まるためです。その代わり、通した記録はそのつど残します。
これは、その場しのぎの妥協ではありません。意図した設計だと記録に明文で残しています。判断の根拠が個人の記憶に留まると、あとから検証も再現もできなくなるためです。
通常のWIP(作業途中の成果物)では、確認メッセージ自体を出さなくなりました。ブロックするのは、承認証跡の無いファイルが納品フォルダへ混入した構造違反1種類だけです。
08機械の設定だけ直すと、AI活用の現場で同じ障害がまた出るのはなぜですか?
フック(機械層)の刷新と同じ日に、指示書側の文言も直しました。「毎回質問する」という古い記述を「作業途中は黙って進める」へ書き換えています。
片方だけを直すと、直さなかった側から同じ症状が再発します。機械が黙っても、指示書に「毎回質問する」とあれば、AIエージェントはその文言に従って質問を出し続けます。逆に指示書だけ直しても、機械側の条件が残れば発火は止まりません。
運用上の論点も1つ残ります。フックの設定ファイルを更新すると、次回Codex起動時に「このフックを信頼するか」という確認が1回だけ出ます。承認するまで新しい仕組みは有効になりません。無効な間も、更新時刻による誤爆はしない設計です。
WEBMARKSは2026-06-24に7部署・30体のAI社員体制を統合し、AI社員同士・AIエンジン同士が同じVaultを並行して触る運用に切り替えました。並行して動くものが増えるほど、間接的な手がかりに頼った設計は壊れます。この事故もその構造から起きた1件です。
明示記録の仕組みは、送信や公開を人が最終判断する承認ゲートの土台にもなります。ゲート設計全体は『AIエージェントの承認ゲート|止める操作4種と3層の選び方』で扱っています。
この章のまとめ
AI活用の現場には、機械の設定と、人が読む指示書という2つの層があります。直すときは同じ日に両方へ手を入れてください。
09次にAI社員の運用で障害が出たとき、原因切り分けはどの順で進めるんですか?
ここまでを、次に同じ症状が出たときへ持ち込める順序へ畳みます。
第1段は、見えたものを書き出すことです。画面に何が並んでいたか、いつから出はじめたか、どれくらいの頻度かを、推測を混ぜずに残します。ここで「たぶんフックだろう」と書くと、以降の調査がその推測に引っ張られます。
第2段は、突き合わせる相手を決めることです。ログの文面だけでは足りません。利用者が見た画面、生成されたファイル、そのセッションが本当に触った対象。少なくとも1つはログ以外と照合します。
第3段は、持ち主を証跡で確かめることです。「このファイルはこのセッションのものだ」と言うとき、根拠が観察による推測か、書いた側が残した記録かを区別します。推測なら、そこが真因の候補です。
第4段は、機械と文章を同じ日に直すことです。設定ファイルと指示書は別の場所にありますが、AIエージェントから見れば同じ1つのふるまいを決めています。片方だけ直した日は、直っていない日と同じだと考えてください。
10よくある質問
更新時刻を判定に使ってはいけない、ということですか
使ってはいけない、という話ではありません。「いつ変わったか」を知りたいときには適した値です。崩れるのは「誰が変えたか」の代わりに使ったときです。処理が1つしか動いていない環境なら推測はよく当たりますが、並行して別の処理が走った瞬間に当たらなくなります。自分の環境で同時に何が動いているかを先に数え、並行するものが1つでもあるなら持ち主の判定には使わないでください。
セッションIDが無いエンジンでは、この方式は使えませんか
IDが用意されていない場合は、こちら側で作ります。今回は、スレッドIDと案件IDを連結した文字列のハッシュを記録先のディレクトリ名にしました。大事なのは、識別子を外から観察して当てるのではなく、書き込む側に名乗らせることです。名乗る仕組みが入れば、エンジン側のID有無は決定的な条件ではなくなります。
誤検知したとき、止める設計と通す設計はどちらが正しいですか
守りたいものによって変わります。今回は、止めると正常な成果物まで巻き込んで業務が止まるため、通す方向を選びました。代わりに、通した事実は記録に残しています。判断を分けるのは「誤って止めたときの損害」と「誤って通したときの損害」のどちらが大きいかです。どちらを選ぶにせよ、選んだ理由を記録に書いておくと、あとから見直せます。
障害の記録には、何を残しておけばよかったんですか
今回足りなかったのは、日ごとの内訳です。合計だけを数えていたため、パッチを当てた後に減ったのかを言えなくなりました。合計は規模を示しますが、推移がないと対策の効き目を判定できません。発生した日付と回数、症状が出た画面の実物、判定に使っていた材料。この3種類を障害が続いているあいだに書き足すと、効き目を数字で確かめられます。
11まとめ|今日やる3つのこと
更新時刻を犯人にしない。この一点でした。原因切り分けは、症状の記述・突き合わせ・証跡・同日修正の4段で進みます。自社が同じ落とし穴の上にいるかは、持ち主の判定を書き出した1行に「時刻」「直近」「最後に更新された」が入るかで分かります。
今日この順で手をつけます
「壊れていない」と書かれた調査結果を1件選び、突き合わせた相手を確認する
相手が書かれていなければ、そこが誤診の入口です
成果物の持ち主をどう判定しているか、仕組みの側を1行で書き出す
推測か記録かが、その1行で分かります
機械の設定と指示書を見直す予定を、同じ日に入れる
片方だけだと、直さなかった側から戻ります
AI検索では、こう聞かれています
AIエージェントの運用で障害が出たとき、原因切り分けはどこから手をつけるんですか?
「AI社員の運用で障害が出たとき、原因切り分けは何から始めるんですか?」の章で説明しています
ログを見て「壊れていない」と出たのに症状が続くのは、なぜですか?
「AIエージェントが…なぜ誤診だったんですか?」の章で扱っています
並行して動くAI社員の成果物は、どうやって持ち主を判定するんですか?
「AI導入を進めた現場で、書き込みの証跡はどう残せばいいんですか?」の章に方式があります
検知が誤作動したとき、止めるのと通すのはどちらへ倒しますか?
「検知の仕組みが誤作動したら、AIエージェントは止める側と通す側のどちらへ倒すんですか?」の章で扱っています
次に読むなら、この記事です