The Go gopher was designed by Renee French.
The design is licensed under the Creative Commons 3.0 Attributions license.
Agent Development Kit For Goがでたので、使ってみた記事です。なので、温かい目でお読み下さい。よろしくお願いいたします。
はじめに
お久しぶりです。o_ga09 です。
コードレビューで使用する「LGTM」画像。ただの承認メッセージに画像を添えるだけで、レビューのやり取りがちょっと楽しくなりますよね。
しかし、毎回同じ画像では飽きてしまうし、かといって自分で画像を探したり作ったりするのは面倒...。そこで、Go言語のマスコットキャラクター「Gopherくん」のかわいいLGTM画像を自動生成するAIエージェントを作ってみました。
この記事では、Google の Agent Development Kit (ADK) を使って、画像生成AIと連携したエージェントシステムを構築した過程を紹介します。
TL;DR
- Agent Development Kit For Goが出たので使ってみた
- 何も思いつかないので、かわいいGopherくんを生成したい
- Agent Development Kit For GoをREST APIで使う際のエンドポイントとかの説明を公式ドキュメントで見つけられず、コードをのぞきにいって解決した
概要
このプロジェクトは、ユーザーの自然言語のリクエストから、Gopherくんが登場する「かわいい」LGTM画像を生成するAIエージェントです。
本アプリケーションはLLM APIの利用料がかかる点や、以下の機能が未実装であることから、現在はローカルでのみ動作させています。
以下が未実装のためです
- 連続で実行された時の制御
- ユーザーを特定して制限する機能
- 課金機能
ちなみに、開発だけで¥176かかりました。
主な機能:
- 自然言語でのリクエスト: 「クリスマスっぽいGopherくんのLGTM画像を作って」といった自由なテキストから画像生成
- 画像の自動保存: 生成した画像をCloudflare R2に自動アップロード
- 画像履歴の管理: 過去に生成した画像の一覧表示とクリップボードへのコピー
- Webインターフェース: React製のモダンなUIで簡単に操作可能
技術スタック:
- バックエンド: Go + Google Gemini API + Agent Development Kit
- 画像ストレージ: Cloudflare R2
- フロントエンド: React + TypeScript + Vite + TanStack Query/Router
動作デモ
Agent Development Kit とは?
Agent Development Kit (ADK) は、Googleが提供するAIエージェント開発フレームワークです。
- Python、Java、Goがある
- Go版は、0.2.0が最新
- Google CloudのAgent Engineは、もちろん、Cloud Runをはじめとした任意のコンテナ実行環境でも動作させることができます
- 今年、4月に初めて発表されたAIエージェント開発フレームワークで、Python、Javaが先行して実装されていました
- 遅れること半年ほどして今年11月にGo版が発表されました
ADKの主な特徴
-
マルチモデル対応
- Gemini、Claude、GPT-4など、複数のLLMモデルに対応
- モデルの切り替えが容易
-
ツールの統合
- Function Callingを使ったツールの定義と実行
- MCP、RAGに対応
-
マルチエージェントに対応
- 任意のサブエージェントを持つことが可能
-
A2Aプロトコルを標準で対応
- こちらも今年、Googleから発表された新しいAIエージェント同士のプロトコルであるA2Aに対応可能
-
セッション管理
- 会話履歴の自動管理
- コンテキストの永続化
-
アーティファクト管理
- 画像やファイルなどのバイナリデータの管理
- ツール間でのデータ受け渡し
-
REST API提供
- 標準化されたAPIエンドポイント
- クライアントからの容易なアクセス
なぜADKを選んだのか
Go版が出たから!
「かわいい」の定義
このエージェントの最大のポイントは、単に「Gopherくんの画像」を生成するのではなく、「かわいい」Gopherくんの画像を生成することです。
「かわいい」を実現するために、プロンプトに以下の要素を組み込んでいます
ビジュアル要素
- キャラクター特性: 大きな瞳、丸みを帯びたフォルム
- 表情: 笑顔、楽しそうな表情
- 色使い: Gopherくんの特徴的な青色を基調とした柔らかい配色
システム構成
┌─────────────────┐
│ Frontend │
│ React + TS │
│ (Port: 5173) │
└────────┬────────┘
│ HTTP/REST
↓
┌─────────────────┐
│ Backend │
│ Go + ADK │
│ (Port: 8080) │
└────────┬────────┘
│
┌────┴─────────────────┐
↓ ↓
┌──────────────┐ ┌──────────────┐
│ Gemini API │ │ Cloudflare │
│ - 2.5 Flash │ │ R2 (Storage) │
│ - Imagen 3 │ │ │
└──────────────┘ └──────────────┘
画像生成フロー
コンポーネント構成
バックエンド (Go)
- Agent: ADKベースのエージェント実装
- Model: Gemini 2.5 Flashとの連携
- Tools: 画像生成・保存ツール
- Server: REST APIサーバー
フロントエンド (React)
- ImageGenerator: メインUI コンポーネント
- API Client: TanStack Queryを使った非同期通信
- Router: TanStack Routerによるルーティング
インフラ
- Cloudflare R2: 画像ストレージ(S3互換)
- Docker: 開発環境(MinIOを使用)
エージェントアーキテクチャ
エージェントの構成
agent := llmagent.New(llmagent.Config{
Name: "gopher-lgtm-image-generator-agent",
Model: model,
Description: "The agent that generates LGTM images based on user requests.",
Instruction: `You are an agent that generates LGTM images based on user requests.
- Use the provided tools to create and manipulate images as needed
- Save the final image to the Cloudflare R2 bucket
- Respond with the URL of the saved image
**【MUST】** Always provide the URL of the saved image in your final response.`,
Tools: []tool.Tool{genImageTool, saveImageTool},
})
ツールの実装
公式のexampleとほぼ一緒です。異なるのは、Cloudfalre R2に保存することくらいです。
そのため、コードは割愛します。
1. GenerateImageTool
画像生成を担当するツール
2. SaveImageTool
画像をCloudflare R2にアップロードするツール
ツール間の連携
ADKのアーティファクト管理機能により、ツール間でのデータ受け渡しが簡潔に実装できています
-
GenerateImageToolが画像を生成し、アーティファクトに保存 - エージェントが次のツール実行を判断
-
SaveImageToolがアーティファクトから画像を取得してR2にアップロード
ここの部分については、以下の1行でArtifactへのSaveとLoadができています。
APIエンドポイント
ADK REST APIのエンドポイントが公式ドキュメントのどこに記載があるのか分からず、実装を見て、今回最低限必要なエンドポイントを使用してアプリケーションを実装しました。
ライブラリのコードを追いやすいのは、Goのいいところ。そしてgoplsありがとうございました!
各エンドポイントの設定箇所
余談ですが、TODO:となっているので、コントリビュートチャンスなのでは!?
エージェント実行ルーティングの定義
上記の通り、セッション作成とエージェント実行などエージェント実行に必要なエンドポイントは、ADKが提供してくれています。
また、画像履歴取得については、さすがに保存した画像を再取得できないと不便なので追加しました。こちらは、ただ、Cloudflare R2(AWS S3互換)にaws-sdk-go-v2を使用して、画像を取得しているだけとなります。
1. セッション作成
POST /v1/agent/apps/{app_name}/users/{user_id}/sessions
新しい会話セッションを作成します。
ここで作成されたsessionIdは、「2. エージェント実行」のリクエストに含めます。
2. エージェント実行
POST /v1/agent/run
リクエストボディ
{
"appName": "gopher-lgtm-image-generator-agent",
"userId": "user-123",
"sessionId": "session-uuid",
"newMessage": {
"role": "user",
"parts": [
{"text": "クリスマスっぽいGopherくんのLGTM画像を作って"}
]
}
}
3. 画像履歴取得
GET /v1/images
Cloudflare R2に保存された画像の一覧を取得します。
レスポンス
{
"images": [
{
"key": "uuid-gopher-lgtm.png",
"url": "https://pub-xxxxx.r2.dev/uuid-gopher-lgtm.png",
"lastModified": "2025-11-30T12:00:00Z",
"size": 524288
}
]
}
フロントエンドでの実装
TanStack Queryを使用した型安全なAPI呼び出し
シンプルにHooksを実装して、APIリクエストするだけです。
プロンプトの工夫
1. エージェントへのインストラクション
You are an agent that generates LGTM images based on user requests.
- Use the provided tools to create and manipulate images as needed
- Save the final image to the Cloudflare R2 bucket
- Respond with the URL of the saved image
**【MUST】** Always provide the URL of the saved image in your final response.
特に重要なのは最後の一文です。エージェントが確実にURLを返すように強制しています。
まとめ
Agent Development Kit (ADK) を使用することで、比較的短期間でマルチモーダルなAIエージェントシステムを構築することができました。
Go Gopherくんの「かわいい」LGTM画像で、あなたのコードレビューをもっと楽しくしてみませんか?Gopherくんかわいいと思った方は、ぜひ、いいねをお願いいたします!
感想
この超シンプル実装では、あまりGoherに似てない画像しか生成されなかったです。というか、普通にGeminiアプリからnano bananaで生成した方が精度良くてあれってなりました。
ですが、AIエージェントとしての改善余地はまだまだあって
- 画像を比較して類似度を計算して検証するサブエージェントを実装する
- プロンプトを洗練する
- Gopherくんの定義やかわいいの定義を明確にする
あたりをもっと詰めれば、もっと良くなりそうだなと思いました。ただ、AIによる自動生成では、学習量の豊富なオリジナル版に似た画像は生成できても本当にオリジナルで自分好みにするのは難しいのだなということを学びました。
GeminiのGopherくん
今回の生成結果



