0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

【個人開発】日本語IMEの不満から始めた拡張はAIエージェントの管制塔になれるのか?

0
Posted at

はじめに

VS Code 拡張「Input Assistant for AI Agents」の 2.0 を公開しました。

もともとは、Windows + WSL の VS Code ターミナルで Claude Code を使うと、日本語 IME の変換中に文字が崩れる、という自分の不便から作り始めた拡張です。入力は専用のパネルで書いて、書き終わったら AI に送る。それだけの道具でした。

使い続けるうちに、Claude Code だけでなく Codex CLI や Gemini CLI も同じ VS Code の中で並べて動かすようになりました。すると、入力の問題は「日本語が崩れる」だけではなくなってきました。

  • どのターミナルに送ったのか分からなくなる
  • 複数行のプロンプトが途中で実行されてしまう
  • 送ったあと、返事が来たのか、承認待ちで止まっているのかが分からない
    2.0 は、この 3 つを片付けるために作り直した版です。名前から「Claude Code」を外したのも、対象を AI コーディングエージェント全般に広げたからです。拡張 ID と設定キーは変えていないので、既存の利用者はそのまま更新されます。

この記事では、2.0 で何を変えたのか、なぜそうしたのか、そして正直に言ってまだ弱いところを書きます。最初のユーザーである自分が欲しかった機能を順番に足していった結果なので、同じような使い方をしている方の参考になれば幸いです。

1.x までの送信先は「概念」だった

1.x の入力タブには、「Claude Code」「OpenAI Codex」「Gemini Code Assist」「VS Code Chat」という送信先のカードが並んでいました。カードを選ぶと、拡張がそれらしいターミナルを探して送る仕組みです。

この方式には、使い込むほど目立つ問題がありました。

一つ目は、同じ種類のターミナルが複数あるときに、どれに送るかを選べないことです。Claude Code を 2 つ立ち上げて別々の作業をさせると、狙っていないほうに送ってしまうことがありました。

二つ目は、ターミナル名だけで判定していたことです。たとえば名前が node のターミナルは Claude Code とみなす、というヒューリスティックでした。当然、誤検出があります。

三つ目は、複数行の扱いです。クリップボード経由で貼り付けると、シェルによっては最後の行以外が 1 行ずつ即実行されてしまいます。1.14 系では確認ダイアログを出して緩和しましたが、根本的な解決にはなっていませんでした。

要するに、送信先が「実際に開いているターミナル」ではなく「Claude Code という概念」だったのが原因です。

2.0 の一つ目の柱、実在するターミナルへ送る

2.0 では、送信先の一覧を今実際に開いているターミナルそのものにしました。入力タブの送信ボタンの上に、開いているターミナルが並びます。

各ターミナルがどのエージェントかは、次の順で判定しています。

  1. ターミナルのシェル情報
  2. シェル統合で取れる、実行中のコマンド行
  3. ターミナル名(最後の手段)
    Claude Code、Codex、Gemini CLI、Grok Build、Copilot CLI、そしてただのターミナルを見分けます。サイドバー版の拡張と VS Code Chat は、その下に並びます。

判定が確定したエージェントのターミナルには、ブラケットペーストで送ります。ブラケットペーストは、貼り付けた文字列を開始と終了の制御シーケンスで囲み、アプリケーション側に「これは 1 回の貼り付けです」と伝える仕組みです。これで複数行のプロンプトが 1 つの入力として届くようになりました。クリップボードを経由しないので、送信のたびに手元のクリップボードが上書きされることもなくなりました。

推測でしか判定できなかったターミナルには、従来どおりクリップボード経由で送ります。確信がないものに Enter まで自動で送るのは危ないからです。

実機で触っていて一つ困ったのが、開いているのは 1 つなのに、一覧に 2〜3 件出る現象でした。原因は、他の拡張が内部用に作った「ユーザーには見せない」ターミナルでした。VS Code の API では、ユーザーから隠す設定で作られたターミナルも取得できてしまいます。2.0 ではこれを除外しています。念のため、ターミナルが開いた・閉じたこと、隠しかどうかを出力パネルに記録するようにしました。まだ余分に出る環境があっても、原因を追えるようにするためです。

二つ目の柱、hook でつながる

送る側が正確になると、次に欲しくなるのは送ったあとの様子でした。

Claude Code には hook という仕組みがあり、セッションの開始、プロンプトの送信、応答の終了、承認の要求などのタイミングで、任意のコマンドを実行できます。Codex や Gemini CLI などにも、似た仕組みがあります。

2.0 では、エージェントタブの「接続」でツールごとにトグルを ON にすると、次の処理をします。

  • 同梱の小さなスクリプト bridge.js を ~/.input-assistant/bridge/ に置く
  • そのツールの hook 設定に、自分用のエントリを 1 つだけ追加する
  • hook が呼ばれるたびに、~/.input-assistant/events/ にイベントを 1 行ずつ追記する
  • 拡張はそのファイルを読んで、画面に反映する
    登録先は次のとおりです。
ツール 登録先
Claude Code ~/.claude/settings.json
Codex ~/.codex/hooks.json
Gemini CLI ~/.gemini/settings.json
Grok Build ~/.grok/hooks/input-assistant.json
Copilot CLI ~/.copilot/settings.json

設計で一番気を使ったのは、ユーザーがすでに書いている他の hook には一切触らないことです。hook の設定ファイルは、人によっては大事な自動化が詰まっている場所です。拡張が勝手に書き換えて壊してしまったら、信頼を失います。拡張をアンインストールすると、自分が追加したエントリだけを消します。

イベントが届くようになると、できることが一気に増えました。

左サイドバーのカードが、生きているセッションの一覧になりました。このウィンドウのものも、別ウィンドウのものも出ます。カードには次の情報が並びます。

  • 入力待ち、応答中、承認待ち、エラー終了の状態
  • 最後に送った内容と返答の 1 行
  • 所要時間
  • コンテキストの使用量ゲージ
  • 承認待ちの件数(アクティビティバーのバッジにも出ます)

別ウィンドウのセッションには「ここで再開」があり、新しいターミナルで resume できます。

履歴にも返答の抜粋が付くようになり、「続きを送る」で同じ送信先に追いの指示を出せます。

プロンプトの本文をイベントファイルに残したくない人向けに、状態と ID だけを保存する設定 cc-input-jp.agents.storePromptText も用意しました。

正直に書くと、hook の入出力の形式はツールごとに違い、しかも各ツールの更新で変わる可能性があります。5 つのツールに対応したことは、そのまま 5 つの保守対象が増えたことでもあります。ここは今後も追いかけ続ける必要があります。

三つ目の柱、組み立て式入力

入力欄そのものも変えました。

1.x では、テンプレートやファイルパスを選ぶと、入力欄の本文に文字列として挿入していました。これだと、本文を書き直すたびに挿入した部分と混ざって、どこまでが自分の文章か分からなくなります。

2.0 では、入力欄の上にチップ行を置きました。チップにできるのは次のものです。

  • Guardrails のオン・オフ
  • 添付するファイル
  • テンプレート
  • エージェントの返答からの引用
  • 英訳して送るのトグル
    送信の瞬間に、これらを決まった順番で組み立てます。
[Guardrails(前置き)]
[引用]
[テンプレート]
[本文]
@path/to/file
[Guardrails(後置き)]

Guardrails は一番外側に付きます。組み立てた結果は「プレビュー」で、実際に送る文字列のまま確認できます。

ファイルは、行頭か空白の直後で @ を打つとパレットがファイルの種類で開き、選ぶとチップになります。Claude Code の @ 参照に慣れている人なら、違和感なく使えると思います。

本文とチップは、プロジェクトごとの下書きとして自動で保存します。Reload Window をしても消えません。長い指示を書いている途中で VS Code を再読み込みして書き直し、という事故が、自分では一番多かったので入れました。

英訳して送るは、本文と引用とテンプレートだけを翻訳して送る機能です。ファイルパスと Guardrails は訳しません。翻訳に失敗したら送信しないようにしました。訳されていない日本語が英語のつもりで届くよりは、止まったほうがいいと判断したためです。履歴には原文と訳文の両方を残します。

画面の整理

機能が増えた分、画面は整理しました。

1.x では最大 8 タブまで増えていたのを、入力、ライブラリ、エージェント、設定の 4 タブにまとめました。ライブラリ・エージェント・設定の 3 つは、左に一覧、右に内容という同じ構造にそろえています。サイドバーの幅に応じて、一覧、アイコンのレール、セレクトの 3 段階に畳みます。

履歴、お気に入り、テンプレート、Skills、ワークスペースのファイルは、Ctrl+K のパレットでまとめて検索できます。

まだ弱いところ

使ってみて気づいた限界も書いておきます。

  • ターミナルの判定は完全ではありません。 シェル統合が効いていない環境では名前頼りになり、その場合は安全側に倒してクリップボード経由になります
  • ブラケットペーストに対応していないシェルもあります。 貼り付けた文字列の前後に 00~ や 01~ が見える場合は、cc-input-jp.send.forceClipboard を ON にしてください
  • hook の形式は各ツールの都合で変わりえます。 動かなくなったら接続を一度オフにして、Issue で教えてもらえると助かります
  • 使用量の表示は非公式のエンドポイントを使っています。 Claude Code 本体が使っているものですが、仕様が変われば表示が止まる可能性があります
  • VS Code 1.118 以降が必要になりました。 それより古い VS Code には、Marketplace から 1.14 系が配られ続けます

移行について

1.x の送信先まわりの設定のうち、実在のターミナル一覧に置き換わって意味がなくなったものは、起動時に自動で削除します。「ターミナルを優先しない」設定にしていた人には、代わりにサイドバー版を一覧に出すよう読み替えます。履歴、お気に入り、テンプレート、プロジェクトはそのまま引き継がれます。

おわりに

2.0 は、自分が毎日 Claude Code と Codex を並べて使う中で「これがないと困る」と感じたものを、一つずつ埋めていった結果です。入力を書く場所、送る先、返事を待つ間の様子を、VS Code の中の 1 か所で見られるようになりました。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?