「gemini-2.5-flashにGoogleSearchツールを渡しているのに、返ってくる回答が去年の情報のまま」「grounding設定をしたはずなのに検索連動しない」——Gemini APIでこの症状にハマる人は多い。原因の大半はツール仕様がGemini 1.5系と2.0/2.5系で変わったことと、検索が実行されたかどうかをレスポンス側で確認していないことの2つに集約される。本記事ではgemini-2.5-flashを前提に、検索連動しない典型パターンと実装修正をコード付きで解説する。
1. Gemini API(gemini-2.5-flash)のGoogleSearchツールが検索連動しない典型パターン
検索連動しない・古い情報を返すケースは、エラーにならず静かに失敗するのが厄介な点だ。APIは200 OKを返し、もっともらしい文章が生成されるため、開発者は「動いている」と誤認しやすい。実際に多い原因は次の3つ。
- Gemini 1.5系のツール名・パラメータ(
google_search_retrieval+dynamic_retrieval_config)をそのまま2.5系のコードに流用している - レスポンスの
grounding_metadataを確認しておらず、検索が実際に走ったか検証できていない - プロンプトが曖昧で、モデルが「検索するまでもない」と自律判断し検索をスキップしている
原因1: google_search_retrieval と google_search の仕様差を混同している
1.5系と2.0/2.5系でツール定義が別物になった
Gemini 1.5系ではgoogle_search_retrievalというツール名で、dynamic_retrieval_configにより「検索するかどうかの閾値」をモデルに渡す仕様だった。ところがGemini 2.0以降(2.5-flashを含む)ではツール名がgoogle_searchに変わり、動的閾値の概念自体が廃止されている。2.0/2.5系ではツールを渡した時点でモデルが必要性を自律判断し、都度検索を実行するかを決める。
モデル系統 | ツール名 | 閾値設定 |
|---|---|---|
Gemini 1.5系 |
|
|
Gemini 2.0 / 2.5系 |
| 不要(モデルが自律判断) |
1.5系のコードをコピーして2.5-flashに使うと、SDKやAPI側が該当パラメータを無視・無効化し、検索が一切走らないまま学習時点の知識だけで応答することがある。これが「検索連動しない」の最大の原因だ。正しい実装は次の通り(google-genaiライブラリ使用)。
from google import genai
from google.genai import types
client = genai.Client(api_key="YOUR_API_KEY")
response = client.models.generate_content(
model="gemini-2.5-flash",
contents="2026年8月時点の最新のPython 3.14の変更点を教えて",
config=types.GenerateContentConfig(
tools=[types.Tool(google_search=types.GoogleSearch())]
),
)
print(response.text)
ここでのポイントはgoogle_search=types.GoogleSearch()という空の設定オブジェクトを渡すだけでよく、1.5系のような閾値指定は不要という点だ。閾値パラメータを付けたまま渡すとSDKのバージョンによってはTypeErrorにならず黙って無視されるため、気づきにくい。
原因2: groundingMetadataを確認しておらず検索の有無が分からない
webSearchQueriesが空なら検索は実行されていない
検索連動しているかどうかは、生成テキストの内容だけでは判断できない。レスポンスに含まれるgrounding_metadataを必ず確認する必要がある。特にweb_search_queriesが空配列の場合、そのターンでは検索が一度も実行されていない。
candidate = response.candidates[0]
metadata = candidate.grounding_metadata
if not metadata or not metadata.web_search_queries:
print("警告: 検索は実行されていません(学習時点の知識のみで応答)")
else:
print("実行された検索クエリ:", metadata.web_search_queries)
for chunk in metadata.grounding_chunks:
print(chunk.web.title, chunk.web.uri)
この検証を入れないまま本番運用すると、「検索したつもりで検索していない」応答をユーザーにそのまま返し続けることになる。特にニュース性の高い情報・料金プラン・APIの仕様変更など鮮度が命の用途では、grounding_metadataのチェックを応答検証の必須項目にするべきだ。
groundingSupportsで根拠箇所を文単位に紐付ける
さらに厳密に裏取りしたい場合はgrounding_supportsを使うと、生成文のどの部分がどの検索結果に基づくかを文単位で取得できる。ユーザー向けに出典リンクを表示するUIを作る際に有用だ。
原因3: プロンプトが曖昧でモデルが検索を省略している
Gemini 2.5系は「検索するかどうか」をモデル自身が判断する設計のため、質問が一般論寄りだと検索をスキップし、学習知識だけで答えてしまうことがある。これも「検索連動しない」と誤解されやすい挙動だ。対策はプロンプト側で明示的に鮮度を要求すること。
- 「最新の」「2026年8月時点の」など具体的な時間軸を明示する
- 「Web検索して裏取りしてから答えて」のように検索利用を明示的に指示する
- 固有名詞・数値・リリース時期など、学習データに含まれにくい情報を尋ねる質問設計にする
それでも検索が実行されない場合は、grounding_metadataの検証結果をもとにリトライするか、検索なし応答であることをユーザーに明示するフォールバック設計にしておくと安全だ。
実装修正: gemini-2.5-flashで検索連動を確実に担保するコード
ここまでの原因を踏まえ、「正しいツール指定」「grounding検証」「検索なしの場合のリトライ」をまとめた実装例が以下だ。
import time
from google import genai
from google.genai import types
client = genai.Client(api_key="YOUR_API_KEY")
def search_grounded_generate(prompt: str, max_retries: int = 2):
for attempt in range(max_retries + 1):
response = client.models.generate_content(
model="gemini-2.5-flash",
contents=prompt,
config=types.GenerateContentConfig(
tools=[types.Tool(google_search=types.GoogleSearch())]
),
)
metadata = response.candidates[0].grounding_metadata
searched = bool(metadata and metadata.web_search_queries)
if searched:
return response.text, metadata.web_search_queries
if attempt 外部API呼び出し全般に言えることだが、レート制限や過負荷エラーへのリトライ実装も合わせて備えておくと安定運用しやすい。この考え方はClaude API 529エラー対処|過負荷時の再試行実装【26年8月】で解説したパターンと共通する部分が多い。
この記事に関連するアイテム
実際に使うものを選ぶ際の参考にどうぞ。
Amazonで「AI開発」を探す
※ 本サイトはAmazonアソシエイト・プログラムの参加者です。紹介リンクを経由してご購入いただいた場合、手数料を受け取ることがあります。
まとめ
Gemini API(gemini-2.5-flash)のGoogleSearchツールが検索連動しない・古い情報を返す原因は、多くの場合エラーではなく1.5系(google_search_retrieval)と2.0/2.5系(google_search)のツール仕様の混同と、grounding_metadataによる検索実行有無の未検証にある。ツール名を正しくgoogle_searchに統一し、レスポンスのweb_search_queriesを必ずチェックする実装に直すだけで、多くのケースは解消する。
業務自動化・スクレイピングの導入をご検討の方はnashiまでお問い合わせください。https://nashi-portfolio.netlify.app