「連結しました」は嘘だった

公開: 2026-09-29
AIエージェントMCP動画生成OpenClawデバッグ

動画生成MCP(Windows機のvideo-genに置いたMCPサーバー)に、2つの機能を足した。**同じ人物を複数の場面で同じ顔にする「登録済みキャラクター」**と、**完成した動画を1本につなぐjoin_videos**だ。miniに常駐させたエージェント(Mini)から、実際に3場面の動画を撮って1本につなげさせる通しテストをした。

1回目の依頼で、Miniは「3本を1本に連結して保存しました」と報告した。実際には、3本の動画を別々に保存しただけだった。join_videosは一度も呼ばれていなかった。

まず機能そのものの話

登録済みキャラクター

同じ人物を別の場面でも同じ顔で出したい、という要望への対応だ。参照画像を使う仕組み自体(ref2va)は前からあったが、エージェントに画像ファイル名を直接渡させるのは避けたかった。

// characters.ts の許可リストの検証。名前は英小文字始まりの32文字以内、
// 画像名は char_ で始まりフォルダ指定を含まないものだけを通す
export const CHARACTER_NAME_RE = /^[a-z][a-z0-9_-]{0,31}$/;
export const CHARACTER_IMAGE_RE = /^char_[a-z0-9_-]{1,40}\.(png|jpg|jpeg|webp)$/;
export const MAX_CHARACTERS = 2;

実機では、mio(黒髪ボブ・眼鏡・トレンチコート)を指定した3場面すべてで同じ人物になった。参照なしでは別人が出る。

動画を1本につなぐ join_videos

それまでMiniが呼べたのは状態確認・生成・ダウンロードの3ツールだけで、結合・切り取り・字幕は呼べなかった。コンテナにffmpegも入っていない。

join_videosは、完了ジョブのID(jobIdかjobId:番号)を配列で受け取り、指定順に1本へつなぐ。サイズ・fps・音声の有無がクリップごとに違っても、先頭のクリップに自動でそろえる。

// join.ts: 先頭のサイズに合わせてscale+pad、24fps・48kHzへ統一。
// 音声が無いクリップには、同じ長さの無音を足してからconcatする
const w = even(clips[0].width);
const h = even(clips[0].height);
const anyAudio = clips.some(c => c.hasAudio);
// clips[i].hasAudio が false なら aevalsrc で無音トラックを生成して結合

結果は新しいjobIdの完了ジョブとして返る。既存の保存コマンド・ダウンロード口がそのまま使える。BGM・字幕・切り取りは付けなかった。H3が音声つきで、今のところ不要という判断だ。

「連結しました」は、なぜ嘘になったか

ここからが今日の本題。3場面(mioを指定、H3プリセット)を生成させたあと、Miniに「1本につなげて」と頼んだ。

1回目(reload前)許可リストに追加toolFilter.includeMiniの実行環境古いツール一覧のまま報告:連結して保存実際は3本を個別保存openclaw mcp reloadキャッシュを捨てて作り直す2回目(reload後)probeが4ツール返却join_videosを実行15.5秒・音声つき1本を保存
ツールを許可リストに足しても、稼働中のエージェントが持つMCP実行環境は作り直されない。reloadで初めて新しい一覧を取りに行く。

openclawのmcp.servers.video-gen.toolFilter.includeにjoin_videosを足し、設定ファイルは更新済みだった。それでもMiniの応答は「連結して保存しました」という嘘の完了報告だった。実際に置かれていたファイルを見ると、3本の動画が別々の名前で保存されているだけだった。

調べると、Miniが持っているMCPクライアントの接続は、起動時に一度ツール一覧を取得したまま保持する作りだった。設定ファイルを書き換えても、その接続は作り直されない。join_videosはMiniから見えていない状態のまま、Miniは「それらしい」応答を返していた。

openclaw mcp reloadでMCPの実行環境を明示的に作り直すと、probe(ツール一覧の取得)が4ツールを返すようになった。その状態で同じ依頼をやり直すと、今度は実際にjoin_videosが呼ばれ、15.5秒・音声つきの1本が保存された。ダウンロードしたファイルのsha256を、Windows側で生成した元ファイルのsha256と突き合わせて一致を確認した。

設定ファイルにツールを足しただけの状態と、openclaw mcp reload後の状態の比較。左は古いツール一覧を保持したままでjoin_videosが見えず、右はreload後に4ツール目が呼び出せるようになっている

2回目のテストで見つかった副作用

reload後の2回目のテストでも、1つ見つかった。mioは女性のキャラクターとして登録したが、2場面目でMiniが書いた説明文がA man ...になっていた。この場面だけ、画面の下に文字のようなものが焼き込まれた(H3は日本語の指示文をセリフと区別できず読み上げる・焼き込む既知の挙動がある)。

エージェントは、登録した人物の性別・外見を取り違えることがある。ツールの説明に「登録された外見の説明に合わせて書く」という一文を足した。

分かったこと

確認したこと結果
許可リストにツールを追加しただけで、稼働中のエージェントに反映されるかされない
openclaw mcp reload後、probeは新しいツールを返すか返す(4ツール)
reload後、実際にjoin_videosが呼ばれ、結果ファイルは元と一致するか一致(sha256)
登録キャラクターは、別の場面でも同じ顔で出るか出る(3場面とも同一人物)
エージェントは登録した人物の性別を正しく扱うか取り違えることがある

最初の「連結して保存しました」という報告を、そのまま信じて次の作業に進んでいたら、3本バラバラのファイルを1本として扱い続けるところだった。エージェントの完了報告は、実行の証拠にならない。 同じ型の失敗は、検査スクリプトが「指摘なし」と表示しながら中身を見ていなかった件(ガードが素通りする書き方)でも起きている。今回は検査ではなくエージェント自身の自己申告だったが、「表示を信じず、実物(ファイル・ハッシュ)を確認する」という直し方は同じだった。

MCPサーバーにツールを足したら、openclaw mcp reloadを実行する。 手順はMCPツール反映漏れに置いた。

このMCPサーバーも、MiniがちょうぼっちやValscopeなどの実装を任されているのと同じ常駐エージェント基盤の上で動いている。