はじめに
前回は対話モードだったので最終的に私が切り貼りを対応していたのですが、この後はAI エージェントを使う都合上、コーディングガードレールを考えることになったので、その振り返りです。
今回「コーディング」ガードレールとしたのは生成AI エージェント提供サービスで考慮する「ガードレール」(例:インジェクションなどの外部攻撃に対する話。機微情報をエージェントが返してしまわないようにする話。過剰請求などの金銭的な問題が発生しないようにする話。法律・倫理に反する返答を返さないようにする話など)の領域は違うという前提で記載をするからです。
あくまで対象は生成AI エージェントのコーディング利用ケースに限定した話をします。
大きく分けると
- エージェント自体を制限するもの
- エージェントの出力コードの品質を調整するためのもの
の2つになります。
これらでエージェントを比較的安全に自立させてそこそこのコードを出力してもらいたいというのが「コーディングガードレール」です。どちらも開発者に対して適応されるものと似ている部分も多くあると思います。制約が弱すぎるとインシデントや品質低下が起こりえますし、制約が強すぎると生産性が落ちたりすることになるかと思います。
エージェント自体を制限するもの
提供元の設定ファイル
流石に提供元も考えてはいるので
- 許可/禁止コマンドリスト
- ルールによる制約
は、ありますが、エージェントが人間の許可を待たずに動作するモードだと守られない例もあるとツール側の説明に明記されていたりします。この点、エージェントが価値を発揮するのは自律動作することなので厳しい点です。
人が他の事をしている時間や、人が働いていない時間帯でも動かしたいという要望はあるはずです。そのさいにエージェントがハマって「許可リストにないコマンドを実行できませんでした」で止まっているのも悲しい話です。
ツールの方でサンドボックスモードを用意しているものもあるようですが、現状、ユーザ向けの非サンドボックス領域操作の機能をエージェントが使ってしまうなどがあるようでなかなかうまくいかない部分もありそうです。
エージェント実行のサンドボックス環境
前段に伴って、OS、ネットワーク、生成したコードの実行前チェックなどができる隔離環境を使うのがより安全ではあるでしょう。ただ、都度の構築がめんどくさいので、リモートのサンドボックス環境が簡単に管理できる仕組みを作らないとなんだろうなとは思います。
どのポイントで権限連携がやりやすいかは提供サービスごとに異なりそうなので、そこはそれぞれのニーズがありそうな気がします(例:クラウドサービスだとVM環境、SCMサービスだとレポジトリ)。
エージェントの出力コードの品質を調整するためのもの
基本設計
SI でのウォーターフォール工程で見かける話になりますが、アーキテクトが対応する工程は人が事前に用意するのがまだよいのかなと思います。
具体的には
- システム概要・要件
- 利用する言語、ミドルウェア、モジュールなどの定義
- データモデル
- プログラム上でのデータ構造
- モジュール (場合によって主要なクラス・インターフェース設計)
- プロトタイプ/サンプル実装の作成
- 開発ガイドライン
等になります。
タスク管理
これからエージェントが実施する内容の一覧を先に作成して順に対応してもらうようにします。あらぬ方向に対応が進まないようにしたり、タスクをある程度の粒度にしてエージェントが一度に扱える範囲での対応ができるようにしていくのが目的です。
タスクに必要な情報も事前に分かっていればこのタスク管理に紐づけておきます。単独エージェントで実装の範囲だけで使うなら、Markdown の TODO リスト書式のテキストで充分だと思います。マルチエージェントの場合はあまり試したことがないのですが、リモートになると MCP Server を介してタスク管理ツールを使うのが良いでしょうか?
タスク一覧や、タスクのある程度の分解・内容の検討は生成AI との対話モードで作っていくのが良いのかなと思います。
タスクの完了条件設定
エージェントが「タスクが終わった」としてよい条件の設定の話です。よくあるのは
- Linter & Formatter でエラーが出ていない事
- 静的解析の定性指標が基準値範囲内であること
- 単体テストを一定のカバー率以上で作成し、すべてパスすること
- リファクタリングの必要性がないかのチェック
などになります。
Linter & Formatter は事前のルール設定をしていれば特にブレることもないので、設定するのがよいと思います。
ただ、残りは生成AI エージェントもある種の賢さを持っているので
- 定性指標のクリアを要件にするとそれに合うハックをはじめる
- 「そのことについては言ってないから」とトンチのような解決方法を使う
ことがありました。
極端な事を言うと「単体テストを書いてすべてパスすること」だと常にパスする単体テストコードを出力するということです。この例だとカバレッジを条件にするとすべてこれで済ませられないので緩和はされると思います。ただ、「そういうことをしたいわけではない」という気持ちになってしまったことはありますが。
また、リファクタリングあたりも適切な説明を与えないとその語から連想されるイメージが異なるのか、期待したものとはズレる内容になったり、うまくいかないケースがありました。開発方法のやり方の指定でも結構ゴリゴリ書いたコードを書き換えていたりするケースもありでうまい方法がまだ見つかっていません。
おわりに
まだ料金を気にしながら使っているところもあってか、「うまく使えないか」ということを主眼にコントロールしがちな対応方法を取っている自覚はあります。とはいえ一晩エージェントが動いて大量のレビューするのが辛い、しかもそこそこ直さないコードができているという日々になってしまうと朝が憂鬱になってしまいます。
これからもどうやったらうまくいくのか、というモデルに寄らない方法がないか探していきたいと思います。