Bedrock本番運用Vol3|Guardrails高度化・Prompt management・Nova生成

目次

1. この記事について — 統制・品質・マルチモーダルを本番で固める

Bedrockアプリの入出力をGuardrailsが統制しPrompt managementがプロンプトをバージョン管理しNova CanvasとReelが画像と動画を生成する統制と品質とマルチモーダルの本番運用全体像
図1: Bedrock Vol3 全体像 — Guardrails統制・Prompt management・Nova マルチモーダル生成
Bedrock 本番運用シリーズ — 領域別ナビゲーション

  • 本Vol3(統制・品質・マルチモーダル生成):Guardrails 高度化(マルチモーダル画像フィルタ・PII・Contextual grounding・Automated Reasoning)/Prompt management(バージョニング・本番デプロイ)/Nova Canvas(画像生成)・Nova Reel(動画生成)
  • Nova モデル選定(Micro/Lite/Pro/Premier)/Flows/Evaluations(LLM-as-Judge)→ Bedrock Vol1 で詳解(本Vol3では再掲せず誘導)
  • Amazon Q 連携/Data Automation/カスタムモデル → Bedrock Vol2 で詳解
Vol3 を読み終えると到達する運用状態

  • Guardrails のマルチモーダル画像フィルタ(GA 2025-03・不適切コンテンツを最大88%ブロック)と Automated Reasoning(業界初の形式論理検証)を本番設計できる
  • Prompt management でプロンプトをバージョン管理し、本番環境へ安全にデプロイ・比較評価できる
  • Nova Canvas で高品質な画像を生成し、Nova Reel で短尺動画をビジネス用途に活用できる

1-1. 本記事のゴール

Amazon Bedrock で生成 AI アプリを本番運用する際、出力の「統制」「品質」「マルチモーダル生成」は開発初期から設計すべき基盤です。出力がどれほど流暢であっても、不適切なコンテンツや機密情報(PII)が混在すれば信頼を失います。プロンプトがコードに埋め込まれていれば、A/B テストや緊急修正のたびにデプロイが必要になります。画像・動画生成を適切な統制なしに運用すれば、ブランドリスクが生じます。

本記事(Bedrock 本番運用 Vol3)は、これらの課題を解決する4分野を体系的に解説します。

Guardrails 高度化では、2025年3月に GA となったマルチモーダル画像フィルタにより、テキストに加えて画像の入出力をポリシーで統制できるようになりました。不適切なマルチモーダルコンテンツを最大88%削減できるとされています。PII フィルタ・denied topics・ワードフィルタと組み合わせることで、アプリ全体の出力ポリシーを一元管理できます。

Contextual grounding check と Automated Reasoning checksでは、前者が参照ソースとクエリをもとにハルシネーションを検出し、後者が業界初の形式論理・数学的検証で出力の事実整合性を保証します。在庫にある製品のみを推奨する、規制要件への準拠を確認するといった業務制約を自動検証できます。

Prompt management(GA 2024-11)では、プロンプトをバージョン管理し、評価・本番デプロイ・バージョン比較を API 経由で実行できます。Converse および InvokeModel でプロンプト識別子を指定することで、コードを変更せずにプロンプトを差し替えられます。

Nova Canvas(画像生成)と Nova Reel(動画生成)の本番運用では、テキストプロンプトから高品質な画像を生成し、inpainting・outpainting・背景除去で編集する Nova Canvas、およびテキスト・画像から短尺動画を生成する Nova Reel の API 設計と Guardrails 連携を解説します。Nova テキストモデル(Micro/Lite/Pro/Premier)の選定については Vol1 で詳解しているため、本記事では再掲せず誘導します。

本記事を読み終えると、Bedrock の「統制・品質・マルチモーダル生成」の3レイヤーを本番グレードで設計・運用する実践力が身につきます。

本番 AI が直面する3層の課題

生成 AI アプリの本番運用では、次の3層の課題が積み重なります。第1層は「安全性・コンプライアンス」の課題です。ユーザーが送信した画像やテキストに含まれる不適切な内容をモデルが処理する前に遮断できていない、PII(個人情報)がログや応答に漏れるといった問題が本番で現実に起きています。

第2層は「品質・信頼性」の課題です。モデルがソース情報に基づかない回答を生成するハルシネーションや、規制・在庫情報と矛盾する回答を出力するケースが含まれます。これらはテスト環境では発見しにくく、本番でユーザーが指摘して初めて顕在化することが多い問題です。

第3層は「運用効率」の課題です。プロンプトをコードに埋め込むと、わずかな文言変更でもデプロイサイクルが必要になります。A/B テストや段階的ロールアウトが困難になり、改善速度が低下します。

Vol3 の4分野はそれぞれこの3層に対応しています。Guardrails(高度化)が安全性・コンプライアンス層をカバーし、Contextual grounding と Automated Reasoning が品質・信頼性層を担い、Prompt management が運用効率層を解決します。Nova Canvas/Reel はこれらの統制基盤の上でマルチモーダル生成を本番運用するための実装を提供します。

1-2. 読者像

本記事は次のような方を主な対象としています。

Amazon Bedrock を使った生成 AI アプリを業務で開発または運用している AWS の開発者・ML エンジニアの方が主な対象です。基本的なモデル推論(InvokeModel / Converse API)の実装経験があり、ストリーミングレスポンスや基本的なプロンプト設計を理解していることを前提とします。

Bedrock の前提知識については、次のいずれかを満たしていると本記事をスムーズに読み進められます。Bedrock Vol1(Nova モデル選定・Flows・Evaluations)を通じて基盤から学んでいる方、または Bedrock コンソールや boto3 での Converse API 呼び出しを日常的に行っている方を想定しています。

本記事が特に役立つ課題は以下のとおりです。出力の安全性・コンプライアンスを強化したい場合、たとえば本番アプリで PII(氏名・クレジットカード番号など)の漏えいを防ぎたい、特定のトピックへの応答を禁止したい、マルチモーダル(テキスト+画像)で統制を設計したい、という方に向けた内容が含まれます。品質の観点では、プロンプトをコードとは独立してバージョン管理したい、Automated Reasoning によるハルシネーション抑制に関心がある方にも適しています。マルチモーダル生成については、Nova Canvas や Nova Reel を広告・EC・社内コンテンツ制作フローに組み込みたい方を想定しています。

前提とする AWS の知識レベルは IAM・VPC の基礎と、Python(boto3)での API 呼び出し経験です。Terraform や CDK によるインフラコード化の経験があると、Guardrails の設定管理のセクションでより深く活用できます。

本記事ではコード例をすべて Python(boto3)で記載しています。モデル呼び出しには bedrock-runtime クライアント、Guardrails・Prompt management の設定 API には bedrock クライアントを使い分けます。AWS 認証情報は環境変数または IAM ロールで設定済みであることを前提とします。

生成 AI の「本番化」では、統制・品質・コスト管理は最後に考えがちですが、後付けで導入するとアーキテクチャ改修が必要になります。本記事が想定する読者は、まさにそのタイミング、すなわちプロトタイプを本番クオリティへ引き上げる段階にいる方です。実装例を通じて、Bedrock の統制・品質保証・マルチモーダル機能を既存アプリに組み込む具体的な方法を学べます。

本記事では扱わない内容として、Bedrock Agents(マルチステップ自律エージェント)の詳細設計・Knowledge Bases の構築・RAG パイプラインの最適化は Vol4 以降の扱いとなります。また、AWS WAF・Shield・Security Hub などの AWS セキュリティサービス全般は本記事のスコープ外です。Guardrails はアプリレベルの出力統制に特化した機能であり、ネットワーク境界防御とは独立して設計します。

1-3. 本シリーズの位置づけと既存記事との棲み分け

Amazon Bedrock 本番運用シリーズは、Bedrock エコシステムの広大な機能を体系的に学べるよう、各 Vol の担当領域を明確に分けた連載です。各 Vol は独立して読めますが、全体像を把握するには Vol1 → Vol2 → Vol3 の順に読み進めることを推奨します。

Bedrock Vol1(基盤・モデル選定編) では、Nova モデルファミリー(Micro・Lite・Pro・Premier)のユースケース別選定指針、Bedrock Flows によるノーコードパイプライン構築、Bedrock Evaluations(LLM-as-Judge)を活用した出力品質評価を深掘りしました。Nova の4モデル比較、Flows のノード設計、評価指標の設計など、Bedrock 活用の基盤となる知識を扱っています。本 Vol3 ではこれらの領域を再掲せず、Vol1 へ誘導します。

Bedrock Vol2(Q連携・カスタムモデル編) では、Amazon Q Business・Q Developer との連携設計、Bedrock Data Automation(文書・画像・動画の自動解析)、カスタムモデル(Fine-tuning・Continued pre-training)によるドメイン特化の手法を扱いました。既存データからモデルを育てるアプローチや、Q エコシステムとの統合パターンに関心がある方は Vol2 を参照してください。

本 Vol3(統制・品質・マルチモーダル生成編) がカバーするのは次の領域です。

Guardrails の高度化については、Vol1 では6箇所程度の言及に留まり専用章がありませんでした。Vol3 では GA 2025-03 のマルチモーダル画像フィルタ・Contextual grounding・Automated Reasoning・PII マスクを専用章として体系的に解説します。Prompt management(GA 2024-11)は、Vol1・Vol2 ともにカバーしていない領域です。プロンプトをバージョン管理・デプロイ・比較評価する実践的な手法を本記事で扱います。

Nova Canvas(画像生成)と Nova Reel(動画生成)については、Vol1 が Nova テキストモデルに集中していたため、マルチモーダル生成の本番運用は未カバーでした。Vol3 では画像・動画生成 API の設計から Guardrails 連携まで解説します。

各 Vol の担当領域を比較した表を以下に示します。

機能領域Vol1Vol2Vol3(本記事)
Nova テキストモデル選定(Micro/Lite/Pro/Premier)◎ 詳解— (Vol1誘導)
Bedrock Flows(ノーコードパイプライン)◎ 詳解— (Vol1誘導)
Bedrock Evaluations(LLM-as-Judge)◎ 詳解— (Vol1誘導)
Amazon Q Business / Q Developer 連携◎ 詳解— (Vol2誘導)
Bedrock Data Automation◎ 詳解— (Vol2誘導)
カスタムモデル(Fine-tuning / CPT)◎ 詳解— (Vol2誘導)
Guardrails 高度化(画像フィルタ・PII・Automated Reasoning)△ 言及のみ◎ 詳解
Prompt management(バージョニング・デプロイ)◎ 詳解
Nova Canvas(画像生成)◎ 詳解
Nova Reel(動画生成)◎ 詳解

この表のとおり、各 Vol は担当機能を完全に分担しています。本 Vol3 のみを読んでも統制・品質・マルチモーダル生成の実装は習得できますが、基盤となる Flows・Evaluations・モデル選定を深く理解するには Vol1 から読み進めることを推奨します。

なお、本記事は目次をテーマが自動生成するため、手動の目次ブロックは設置していません。

Vol3 で学んだ内容を実務に活かす3ステップ

本記事を読み終えた後、実務への適用は次の順序で進めることを推奨します。

ステップ1:Guardrails の設計と評価(§2〜§3)。まず既存アプリに Guardrails を組み込み、入出力の統制基盤を構築します。コンテンツポリシー・PII マスク・denied topics を設定し、CloudWatch Metrics でブロック率を2週間モニタリングします。誤検知が一定率以下に収まったら次のステップへ進みます。

ステップ2:Prompt management の導入(§4)。Guardrails が安定したら、プロンプトをコードから切り離し Prompt management で管理します。既存のハードコードされたプロンプトを順次移行し、バージョニングとデプロイフローを確立します。A/B テストやロールバックが容易になり、運用負荷が大幅に下がります。

ステップ3:マルチモーダル生成の本番化(§5〜§6)。Guardrails と Prompt management の基盤が整ったら、Nova Canvas・Nova Reel を組み込んでマルチモーダル生成を本番化します。ステップ1で設定した Guardrails を画像・動画生成にも適用することで、テキストと同一のポリシーで統制できます。

各ステップは段階的に導入できるため、既存の Bedrock アプリを一度にリアーキテクチャする必要はありません。Guardrails 単体から始め、安定が確認できたら Prompt management を追加し、最後にマルチモーダル生成へと段階的に拡張するアプローチが、本番運用リスクを最小化します。

それでは §2 以降で各機能の実装詳細を解説します。

基盤・モデル選定編:Bedrock Vol1(Flows/Nova選定/Evaluations)を読む
Q連携・カスタムモデル編:Bedrock Vol2 を読む


2. Guardrails 高度化① — マルチモーダル画像フィルタと機密情報

Guardrailsがテキストと画像の入出力をコンテンツフィルタとdenied topicsとPIIフィルタで検査し有害コンテンツと機密情報を遮断するマルチモーダル統制フロー
図2: Guardrails マルチモーダル統制 — 画像フィルタ・denied topics・PII

2-1. マルチモーダル画像コンテンツフィルタ

Amazon Bedrock Guardrails の画像コンテンツ検査機能は、2025年3月に GA(一般提供)となりました。re:Invent 2024 でプレビューが発表された機能で、テキストに加えて画像の入出力を統一されたポリシーで統制できる点が特徴です。AWS の公式情報によると、マルチモーダルコンテンツへの安全ポリシー適用により、問題のあるコンテンツを最大88%削減できるとされています。

仕組みと対応モデル

画像フィルタは、コンテンツ検査ロジックをテキストと画像の両方に適用します。具体的には、不適切表現・過激な描写・嫌悪表現・自傷行為助長・誤情報促進の5カテゴリを対象とし、各カテゴリで画像入力の検査を有効化できます。

対応しているのは、Amazon Nova シリーズと Anthropic Claude(Claude 3 以降)など、マルチモーダル入力に対応したモデルです。Guardrails はモデルへの入力(ユーザーが送信する画像・テキスト)とモデルの出力(生成テキスト)の両方で機能し、入力段階で問題のある画像を検出した場合はモデル呼び出し自体をスキップして拒否メッセージを返します。

しきい値設計のポイント

各カテゴリのしきい値は NONE・LOW・MEDIUM・HIGH の4段階で設定します。NONE はそのカテゴリの検査を無効化し、HIGH は感度を最大にします。本番設計では、ユースケースのリスク許容度に合わせてカテゴリごとに独立して設定します。

業務向けアプリでは複数のカテゴリを HIGH へ設定し、医療情報提供などコンテキスト依存のアプリでは特定カテゴリのしきい値を LOW まで緩和するといった調整が可能です。しきい値を高くしすぎると誤検知が増え、正当なコンテンツがブロックされます。特に画像では、医療系の解剖図や工業用の機器写真など、業務コンテキストでは適切ながら一般的な基準では高スコアとなる画像は要注意です。

CloudWatch Metrics の InvocationInput/OutputFilteredCount でブロック率を継続的に監視し、しきい値を調整することを推奨します。

API 設計例:画像フィルタ付き Guardrails の作成

以下は Python(boto3)で画像フィルタを有効にした Guardrails を作成する例です。inputModalities"IMAGE" を追加することで、テキストと同様に画像の統制が有効になります。

import boto3

bedrock = boto3.client("bedrock", region_name="us-east-1")

response = bedrock.create_guardrail(
 name="multimodal-guardrail-v1",
 description="テキスト・画像の統合コンテンツポリシーガードレール",
 contentPolicyConfig={
  "filtersConfig": [
{
 "type": "SEXUAL",
 "inputStrength": "HIGH",
 "outputStrength": "HIGH",
 "inputModalities": ["TEXT", "IMAGE"],
 "outputModalities": ["TEXT"],
},
{
 "type": "VIOLENCE",
 "inputStrength": "HIGH",
 "outputStrength": "HIGH",
 "inputModalities": ["TEXT", "IMAGE"],
 "outputModalities": ["TEXT"],
},
{
 "type": "HATE",
 "inputStrength": "MEDIUM",
 "outputStrength": "HIGH",
 "inputModalities": ["TEXT", "IMAGE"],
 "outputModalities": ["TEXT"],
},
{
 "type": "INSULTS",
 "inputStrength": "MEDIUM",
 "outputStrength": "MEDIUM",
 "inputModalities": ["TEXT", "IMAGE"],
 "outputModalities": ["TEXT"],
},
{
 "type": "MISCONDUCT",
 "inputStrength": "MEDIUM",
 "outputStrength": "MEDIUM",
 "inputModalities": ["TEXT", "IMAGE"],
 "outputModalities": ["TEXT"],
},
  ]
 },
 blockedInputMessaging="入力されたコンテンツはポリシーに反するため処理できませんでした。",
 blockedOutputsMessaging="出力されたコンテンツはポリシーに反するためブロックされました。",
)
guardrail_id = response["guardrailId"]
guardrail_version = response["version"]
print(f"Guardrail 作成完了: {guardrail_id} (version: {guardrail_version})")

Converse API での画像フィルタ適用

Guardrails を Converse API に適用するには guardrailConfig パラメータを指定します。画像はバイナリとして content リストに含めます。

import base64
import boto3

bedrock_runtime = boto3.client("bedrock-runtime", region_name="us-east-1")

with open("input_image.png", "rb") as f:
 image_bytes = f.read()

response = bedrock_runtime.converse(
 modelId="amazon.nova-pro-v1:0",
 messages=[
  {
"role": "user",
"content": [
 {
  "image": {
"format": "png",
"source": {"bytes": image_bytes},
  }
 },
 {"text": "この画像に写っている内容を説明してください。"},
],
  }
 ],
 guardrailConfig={
  "guardrailIdentifier": guardrail_id,
  "guardrailVersion": guardrail_version,
  "trace": "enabled",
 },
)

output = response["output"]["message"]["content"][0]["text"]
trace = response.get("trace", {})
print(f"出力: {output}")
print(f"Guardrail アクション: {trace.get('guardrail', {}).get('inputAssessment', {})}")

trace: "enabled" を設定すると、Guardrails がどのポリシーに基づいてアクションを取ったかをレスポンスの trace フィールドで確認できます。検査ログは CloudWatch Logs へ転送でき、誤検知の分析に活用できます。

2-2. denied topics・機密情報(PII)・ワードフィルタ

Guardrails は画像コンテンツフィルタ以外にも、denied topics・機密情報(PII)マスク・ワードフィルタの3つのポリシーを組み合わせて、アプリ全体の出力統制を実現します。これらはコンテンツフィルタと独立して設定でき、特定のビジネス要件に対応できます。

denied topics(禁止トピック)

denied topics は、アプリの用途範囲外のトピックへの応答を禁止するポリシーです。金融アドバイス専用アプリが競合製品を比較しないようにする、社内サポートボットが政治的議論への応答を禁止するといった制御に使います。

トピックは自然言語の「定義」と「例文」で定義します。Guardrails が定義に合致する入力または出力を検出した場合、設定済みのブロックメッセージを返します。

import boto3

bedrock = boto3.client("bedrock", region_name="us-east-1")

response = bedrock.create_guardrail(
 name="topic-guardrail-v1",
 description="禁止トピック設定ガードレール",
 topicPolicyConfig={
  "topicsConfig": [
{
 "name": "競合製品の比較",
 "definition": "自社製品と他社製品を比較したり、競合他社を推奨したりするコンテンツ",
 "examples": [
  "A社とB社はどちらが優れていますか",
  "競合製品と比較して教えてください",
 ],
 "type": "DENY",
},
{
 "name": "投資アドバイス",
 "definition": "特定の金融商品への投資を推奨・助言するコンテンツ",
 "examples": [
  "この株を買うべきですか",
  "どの銘柄が値上がりしますか",
 ],
 "type": "DENY",
},
  ]
 },
 blockedInputMessaging="このトピックにはお答えできません。",
 blockedOutputsMessaging="このトピックにはお答えできません。",
)

トピック定義の精度は、定義文と例文の質に依存します。定義が曖昧すぎると誤検知が増え、例文が少なすぎると検出漏れが発生します。本番では10件以上の例文を用意し、テスト段階で誤検知率を評価してから GA することを推奨します。

機密情報(PII)マスク

PII(個人を特定できる情報)フィルタは、モデルの入力・出力に含まれる機密情報を検出して置換またはブロックします。対応するカテゴリには、氏名・メールアドレス・電話番号・クレジットカード番号・社会保障番号(SSN)・IP アドレスなど多数が含まれます。

PII フィルタには MASK と BLOCK の2つのアクションがあります。MASK は該当箇所をプレースホルダーに置き換えて応答を継続します。BLOCK は該当情報を含む入力または出力全体を拒否します。顧客向けサポートボットでは MASK を使い、社内分析ログへの書き込み前に BLOCK を使うといった使い分けが有効です。

response = bedrock.create_guardrail(
 name="pii-guardrail-v1",
 description="PII マスク・ブロック設定ガードレール",
 sensitiveInformationPolicyConfig={
  "piiEntitiesConfig": [
{"type": "NAME",  "action": "MASK"},
{"type": "EMAIL", "action": "MASK"},
{"type": "PHONE", "action": "MASK"},
{"type": "CREDIT_DEBIT_CARD_NUMBER",  "action": "BLOCK"},
{"type": "US_SOCIAL_SECURITY_NUMBER", "action": "BLOCK"},
{"type": "IP_ADDRESS",  "action": "MASK"},
  ],
  "regexesConfig": [
{
 "name": "社員番号",
 "description": "社内社員番号パターン EMP-XXXXXXXX",
 "pattern": "EMP-\\d{8}",
 "action": "MASK",
}
  ],
 },
 blockedInputMessaging="入力に機密情報が含まれています。ご確認の上、再度お試しください。",
 blockedOutputsMessaging="出力にお客様の機密情報が含まれていたため一部をマスクしました。",
)

regexesConfig を使うと、標準の PII カテゴリに加えて独自の正規表現パターン(社員番号・内部 ID・製品シリアルなど)を定義してマスクできます。カスタム正規表現は最大10件まで設定可能です。

MASK の場合、出力では {NAME}{EMAIL} のようなプレースホルダーに置換されます。アプリ側でプレースホルダーをそのままユーザーに表示するか、元データと突合して復元するかはユースケースによって選択します。機密性が高い場面では BLOCK を優先し、ユーザーへの有用性を最大化したい場面では MASK を選択するのが基本方針です。

ワードフィルタ

ワードフィルタは、特定の単語やフレーズを入力・出力から除外するシンプルなポリシーです。商標名・競合製品名・社内で使用禁止とされた用語などを直接指定できます。denied topics が意味的なパターンを対象とするのに対して、ワードフィルタは表記の完全一致に基づいてブロックします。

response = bedrock.create_guardrail(
 name="word-filter-guardrail-v1",
 description="ワードフィルタ設定ガードレール",
 wordPolicyConfig={
  "wordsConfig": [
{"text": "競合社名A"},
{"text": "競合社名B"},
{"text": "社外秘キーワード"},
  ],
  "managedWordListsConfig": [
{"type": "PROFANITY"},
  ],
 },
 blockedInputMessaging="使用できないキーワードが含まれています。",
 blockedOutputsMessaging="使用できないキーワードが含まれていたためブロックされました。",
)

managedWordListsConfigPROFANITY を指定すると、AWS が管理する冒涜的表現リストを自動適用できます。独自の単語リストと組み合わせることで、社内コンプライアンス要件と一般的な品質基準を同時に満たせます。ワードフィルタは大文字小文字の区別をしないため、表記揺れ(英語)にも対応します。

2-3. アプリ横断運用パターン

Guardrails は単一の定義を複数のアプリ・エージェントで共有して適用できます。組織内で統一されたポリシーを維持するには、Guardrail ID とバージョンを組織の設定管理(AWS Systems Manager Parameter Store または AWS AppConfig)に保存し、各サービスが起動時に取得するパターンが本番環境で標準的です。

import boto3

ssm = boto3.client("ssm", region_name="us-east-1")

# Guardrail ID とバージョンを Parameter Store で管理
ssm.put_parameter(
 Name="/myapp/guardrail/id",
 Value="grd-xxxxxxxxxxxxxxxx",
 Type="String",
 Overwrite=True,
)
ssm.put_parameter(
 Name="/myapp/guardrail/version",
 Value="2",
 Type="String",
 Overwrite=True,
)

# 各サービスが起動時に取得する
def get_guardrail_config() -> dict:
 guardrail_id = ssm.get_parameter(Name="/myapp/guardrail/id")["Parameter"]["Value"]
 guardrail_version = ssm.get_parameter(Name="/myapp/guardrail/version")["Parameter"]["Value"]
 return {"guardrailIdentifier": guardrail_id, "guardrailVersion": guardrail_version}

バージョン管理の鉄則: Guardrails の設定は DRAFT バージョンで編集し、テスト完了後に create_guardrail_version で本番バージョンを確定します。本番アプリは常に特定の数値バージョンを参照し、DRAFT を本番環境に向けないことが重要です。バージョンは不変のスナップショットであるため、ロールバックが必要な場合は旧バージョン番号を Parameter Store に戻すだけで完了します。

誤検知の継続的な改善: GuardrailCoverageGuardrailEngaged の CloudWatch Metrics を週次でレビューし、誤検知率が一定閾値を超えた場合はしきい値を調整します。本番 Guardrail の変更は必ずステージング環境で評価してから新しいバージョンを切り、数値バージョンを本番に適用します。


3. Guardrails 高度化② — Contextual grounding と Automated Reasoning

Contextual groundingが参照ソースとクエリでハルシネーションを検出しAutomated Reasoningが形式論理でモデル出力の事実整合を検証するハルシネーション抑制フロー
図3: ハルシネーション抑制 — Contextual grounding と Automated Reasoning

3-1. Contextual grounding check

Contextual grounding check は、RAG(Retrieval Augmented Generation)パターンにおけるハルシネーション(事実誤認)を自動検出するガードレール機能です。モデルの回答が取得した参照ソース文書に基づいているかを定量スコアで評価し、しきい値を下回る場合に自動ブロックまたはフラグを立てます。Vol1 で紹介した Evaluations(モデル評価)とは異なり、本機能はリアルタイムの本番推論パスに組み込んで使用します。

2 種類のスコアと評価対象

Contextual grounding check は 2 つのスコアで評価します。

  • Grounding score(根拠スコア): モデルの回答が参照ソース文書の内容に忠実かを測定します。参照ソースに記載されていない情報を回答に含めている場合にスコアが下がります。
  • Relevance score(関連スコア): ユーザーのクエリに対して参照ソース文書が適切かを測定します。クエリと無関係な文書が取得されている場合にスコアが下がります。

両スコアはそれぞれ 0〜1 の範囲で計算されます。各スコアにしきい値(threshold)を設定し、しきい値を下回る場合にガードレールがブロック応答を返します。

しきい値の選定基準

しきい値の設定は用途によって調整が必要です。

用途GroundingRelevance考え方
金融・医療などの高精度要件0.85〜0.950.80〜0.90誤情報のコストが高いため厳格に設定
社内 FAQ チャットボット0.70〜0.800.70〜0.80ある程度の柔軟性を持たせてユーザー体験を優先
カスタマーサポート0.75〜0.850.75〜0.85誤回答はコスト増につながるため中程度に設定

低すぎるしきい値はハルシネーションを見逃し、高すぎるしきい値は正しい回答まで誤ブロックします。CloudWatch の GuardrailEngaged メトリクスを週次でレビューし、誤検知率をベースに継続的に調整することを推奨します。

Guardrail 作成 — Contextual grounding 設定

import boto3

bedrock = boto3.client("bedrock", region_name="us-east-1")

response = bedrock.create_guardrail(
 name="contextual-grounding-guardrail-v1",
 description="RAG 回答のハルシネーション検出ガードレール",
 contextualGroundingPolicyConfig={
  "filtersConfig": [
{
 "type": "GROUNDING",
 "threshold": 0.75,  # 社内 FAQ 用・必要に応じて調整
},
{
 "type": "RELEVANCE",
 "threshold": 0.75,
},
  ]
 },
 blockedInputMessaging="お問い合わせ内容を確認できませんでした。",
 blockedOutputsMessaging="回答の根拠情報が不足しているため、正確な情報をお伝えできません。",
)
guardrail_id = response["guardrailId"]

Converse API への組み込み

Contextual grounding を有効化した Guardrail を Converse API に適用する際は、参照ソース文書を grounding_source として明示的に渡す必要があります。参照ソースを渡さない場合、grounding check は動作しません。

import boto3

bedrock_rt = boto3.client("bedrock-runtime", region_name="us-east-1")

# RAG パイプラインで取得した参照ソースとユーザーのクエリを組み合わせて渡す
retrieved_context = "(ナレッジベース検索で取得した文書テキストをここに含める)"
user_query = "サービスの返品条件を教えてください。"

response = bedrock_rt.converse(
 modelId="amazon.nova-pro-v1:0",
 messages=[
  {
"role": "user",
"content": [
 {
  "guardContent": {
"text": {
 "text": retrieved_context,
 "qualifiers": ["grounding_source"],
}
  }
 },
 {
  "text": user_query,
 },
],
  }
 ],
 guardrailConfig={
  "guardrailIdentifier": guardrail_id,
  "guardrailVersion": "1",
  "trace": "enabled",
 },
)

output = response["output"]["message"]["content"][0]["text"]
guardrail_trace = response.get("trace", {}).get("guardrail", {})
print(output)

trace: "enabled" を指定すると、ガードレールの評価詳細(各スコア・ブロック理由など)をレスポンスの trace フィールドから取得できます。本番環境での誤検知分析や閾値チューニングに活用できます。

主なユースケース

  • 社内ナレッジベース FAQ: HR マニュアルや IT 規定を参照ソースとして、モデルが就業規則と無関係の情報を回答しないよう制約します。
  • カスタマーサポート: 製品マニュアルや FAQ を参照ソースとして、サポートエージェントが根拠のない情報を顧客に伝えるリスクを軽減します。
  • 医療・法律の QA: 診療ガイドラインや法令を参照ソースとして、その文書範囲内でのみ回答させるよう厳格に制御します。

Contextual grounding check は Amazon Bedrock ナレッジベース(KB)と組み合わせるのが典型的なパターンです。KB が返す検索結果テキストを grounding_source として渡すことで、RAG パイプライン全体のハルシネーション耐性を一元管理できます。Vol1 で解説した Bedrock KB との統合では、retrieve API の retrievalResults をそのまま guardContent に渡すことで実装できます。

3-2. Automated Reasoning checks(形式論理)

Automated Reasoning checks は、業界初の形式論理(Formal Logic)ベースの検証機能です。AWS re:Invent 2024 でプレビュー発表された後、GA(一般提供)となりました。大規模言語モデルが生成した回答を、自然言語で定義したポリシー文書(Policy document)に照らして論理検証し、ルール違反を検出します。統計的手法では見落としがちな「根拠に欠ける断言」や「条件節の誤適用」を形式論理で捕捉できる点が、Contextual grounding check との大きな違いです。

形式論理ベース検証のしくみ

Automated Reasoning checks は 3 段階で動作します。

  1. ポリシー定義: 自然言語でビジネスルールや制約を記述したポリシー文書を Bedrock Guardrails に登録します。
  2. 形式論理変換: Bedrock がポリシーを内部的に形式論理(一階述語論理・数理制約など)に変換します。
  3. 回答検証: モデルの出力をポリシーの論理制約と照合し、矛盾や違反を検出してブロックします。

例えば「在庫にある商品のみを推奨する」というルールは、在庫テーブルの状態とモデルの回答内容を論理的に照合することで、モデルが在庫切れ商品を誤って推奨するのを防ぎます。「元本保証」や「必ず利益が出る」という表現を禁止するポリシーを定義すれば、金融コンプライアンス上のリスクを自動的に排除できます。

ポリシー記述のベストプラクティス

ポリシーは自然言語で記述します。形式論理への変換は Bedrock 側で自動的に行われるため、論理式を直接記述する必要はありません。

  • 単純な条件文で書く: 「もし〜であれば、〜してはならない」の形式で記述すると変換精度が高くなります。
  • 定量的な制約を明記する: 「金利は年率 20% を超えてはならない」のような数値制約は変換精度が高まります。
  • 矛盾を避ける: 相反するルールが混在すると検証エンジンが常に違反と判定するため、ポリシーの一貫性を確認してから登録します。

ポリシー登録と Guardrail 設定例

import boto3

bedrock = boto3.client("bedrock", region_name="us-east-1")

# 金融コンプライアンス向けポリシー文書(自然言語で記述)
policy_document = """
## 投資アドバイスポリシー

ルール1: 元本保証の禁止
投資商品について「元本が保証されている」「必ず利益が出る」という表現は使用しない。
すべての投資商品にリスクがある旨を必ず明記する。

ルール2: 利回りの断言禁止
具体的な利回りを提示する場合は過去の実績であることを明記し、
将来の利回りを確定的に断言しない。

ルール3: リスク説明義務
金融商品取引法の規制対象商品については、リスク説明と商品分類を必ず明示する。
"""

# Automated Reasoning ポリシーを登録し Guardrail に紐付ける
# 詳細な API パラメータは Bedrock Guardrails API リファレンスを参照
response = bedrock.create_guardrail(
 name="automated-reasoning-finance-v1",
 description="金融コンプライアンス向け Automated Reasoning ガードレール",
 automatedReasoningPolicyConfig={
  "document": policy_document,
 },
 blockedInputMessaging="ご質問の内容を確認中です。改めてお問い合わせください。",
 blockedOutputsMessaging="コンプライアンスポリシーに照らし、この情報の提供はできません。",
)
guardrail_id = response["guardrailId"]

Converse API での利用

Automated Reasoning check を有効化した Guardrail は、他のポリシーと同じく Converse API で利用できます。

import boto3
import json

bedrock_rt = boto3.client("bedrock-runtime", region_name="us-east-1")

response = bedrock_rt.converse(
 modelId="amazon.nova-pro-v1:0",
 messages=[
  {
"role": "user",
"content": [
 {
  "text": "A 社のファンドは元本保証で年利 10% が期待できますか?",
 }
],
  }
 ],
 guardrailConfig={
  "guardrailIdentifier": guardrail_id,
  "guardrailVersion": "1",
  "trace": "enabled",
 },
)

output = response["output"]["message"]["content"][0]["text"]
trace = response.get("trace", {}).get("guardrail", {})
if trace:
 print("ポリシー評価結果:", json.dumps(trace, indent=2, ensure_ascii=False))

ポリシー違反が検出された場合、output には blockedOutputsMessaging で設定したメッセージが返されます。trace には違反したルールの詳細が含まれており、どの制約に抵触したかを特定できます。

主なユースケース

  • 金融規制遵守: 投資アドバイス・保険商品説明における法的表現ルールをポリシー化し、金融商品取引法・保険業法に違反する表現を自動検出します。コンプライアンス担当者が自然言語でポリシーを管理できるため、法改正時の迅速な対応が可能です。
  • 医療記録・診断支援: 「確定診断」「治癒保証」などの断言的表現を禁止するポリシーを定義し、AI が不適切な確定的表現を患者に伝えるリスクを防ぎます。
  • 法的文書レビュー: 契約書の標準条項からの逸脱を形式論理で検出し、法務担当者のレビュー負担を軽減します。
  • EC サイトの商品推薦: 在庫状況・価格制約をポリシーに定義し、在庫切れ商品の誤推薦を防ぎます。

Contextual grounding check との組み合わせ

Contextual grounding check は「モデルの回答が参照ソースから逸脱していないか」を統計的に評価します。Automated Reasoning checks は「定義されたビジネスルールや論理制約に違反していないか」を形式的に検証します。両機能は補完的な関係にあり、高い信頼性が求められるシステムでは両者を組み合わせることで多層的なハルシネーション・誤情報防止が実現できます。Guardrails には複数のポリシーを同時に設定できるため、1 つの Guardrail に Contextual grounding と Automated Reasoning を共存させて運用することを推奨します。


4. Prompt management — バージョニングと本番デプロイ

Prompt managementでプロンプトを作成しバージョンスナップショットを切りConverseやInvokeModelがPrompt識別子で本番実行しバージョン比較で最適化するプロンプト管理フロー
図4: Prompt management — バージョニング・本番デプロイ・比較

4-1. プロンプトの作成・変数・バージョン

Amazon Bedrock Prompt management は 2024 年 11 月に GA(一般提供)となったプロンプト管理サービスです。プロンプトをアプリケーションコードから切り離し、バージョン管理・評価・デプロイを一元化することで、本番環境のプロンプト品質を継続的に高められます。Nova モデル選定や Flows・Evaluations の基礎については Vol1 で扱っているため、本セクションでは Prompt management 固有の機能に集中します。

Prompt management が解決する課題

プロンプトをコードにハードコードすると、文言の微調整のたびにアプリケーションのデプロイが必要になります。複数の開発者が各自の環境でプロンプトを書き換えると、どのバージョンが本番に稼働しているかが追跡できなくなります。Prompt management を導入することで次の4点が実現できます。

  • プロンプトの変更をコード変更なしに本番反映できる
  • バージョン(スナップショット)で変更履歴を厳密に管理できる
  • テストセットで複数バージョンを定量的に比較評価できる
  • チームメンバーが IAM で権限分離してプロンプトを管理できる

プロンプトの作成

マネジメントコンソールの Bedrock → Prompt management から新規プロンプトを作成できます。System prompt と User message template を定義し、モデルとパラメータ(temperature / top-p / max tokens)をプロンプトリソースに紐付けます。API 経由での作成には CreatePrompt オペレーションを使います。

import boto3

bedrock = boto3.client("bedrock", region_name="us-east-1")

response = bedrock.create_prompt(
 name="customer-support-v1",
 description="カスタマーサポート向け汎用プロンプト",
 variants=[
  {
"name": "default",
"modelId": "amazon.nova-pro-v1:0",
"templateType": "TEXT",
"templateConfiguration": {
 "text": {
  "text": (
"あなたは {{company_name}} のカスタマーサポート担当です。\n"
"以下の問い合わせに対して、親切・丁寧・簡潔に回答してください。\n\n"
"問い合わせ内容:\n{{customer_query}}"
  ),
  "inputVariables": [
{"name": "company_name"},
{"name": "customer_query"},
  ],
 }
},
"inferenceConfiguration": {
 "text": {
  "temperature": 0.3,
  "topP": 0.9,
  "maxTokens": 1024,
 }
},
  }
 ],
)

prompt_id = response["id"]
print(f"プロンプト ID: {prompt_id}")

変数と動的プロンプト

プロンプトテンプレートには {{変数名}} 形式で変数を埋め込めます。使用できる文字はアルファベット・数字・アンダースコアです。実行時に変数値を渡すことで、同一のテンプレートを複数ブランドや複数ユースケースに流用できます。たとえば company_name を変えるだけで、同じプロンプトを複数の企業サービス向けに再利用できます。変数が未解決のまま実行すると UNRESOLVED_VARIABLE エラーになるため、すべての変数に値を渡すことが必須です。

バージョン(スナップショット)

プロンプトを承認するタイミングで CreatePromptVersion を呼び出すとバージョンが作成されます。バージョンは不変のスナップショットであり、作成後は内容を変更できません。これにより、どのバージョンが本番に稼働しているかを確実に追跡できます。

version_resp = bedrock.create_prompt_version(
 promptIdentifier=prompt_id,
 description="v1.0: 初回リリース。敬語トーンに統一。",
)
version_num = version_resp["version"]
print(f"バージョン番号: {version_num}")

バージョン番号はゼロパディングなしの整数(1, 2, 3 …)で自動採番されます。description フィールドをリリースノート代わりに使い、「どの課題を解決したバージョンか」を記録する運用が効果的です。バージョン管理の鉄則は、DRAFT バージョンで編集し、テスト完了後にバージョンを確定する手順を守ることです。本番アプリは常に特定の数値バージョンまたは後述のエイリアスを参照し、DRAFT を本番環境に向けてはいけません。

評価機能

コンソールのプロンプト画面では、テスト入力データセットを用意して複数バージョンのレスポンスを並べて比較できます。評価基準(正確性・トーン・有害性)を人手または LLM で採点し、最良バージョンを本番に昇格させるワークフローを構築できます。チームで評価する場合は、評価結果を Amazon S3 にエクスポートして全員が同一データを参照できる体制を整えると効果的です。LLM-as-Judge を使った系統的な評価設計については Vol1 の Evaluations セクションを参照してください。


4-2. 本番デプロイと Converse/InvokeModel での実行

バージョンの本番デプロイ(エイリアス)

承認済みバージョンを本番デプロイするには エイリアス を使います。エイリアスはバージョンへの名前付きポインタです。CreatePromptAlias でエイリアスを作成し、向き先バージョンを指定します。

alias_resp = bedrock.create_prompt_alias(
 promptIdentifier=prompt_id,
 name="production",
 routingConfiguration=[
  {"promptVersion": version_num, "promptVariantName": "default"}
 ],
)
alias_id = alias_resp["id"]
print(f"エイリアス ID: {alias_id}")

エイリアスの最大の利点は、本番アプリケーションのコードを変更せずにプロンプトバージョンを切り替えられる点です。production エイリアスが指すバージョンを更新するだけで即時に本番反映されます。緊急のプロンプト修正もコードデプロイなしで完了できます。ロールバックが必要な場合は旧バージョン番号をエイリアスに設定し直すだけで完了します。

A-B テスト

routingConfiguration に複数バージョンをリストアップすると、リクエストがランダムに分散されます。Bedrock がトラフィック配分をフルマネージドで行うため、追加インフラは不要です。

ab_alias_resp = bedrock.create_prompt_alias(
 promptIdentifier=prompt_id,
 name="ab-test",
 routingConfiguration=[
  {"promptVersion": "1", "promptVariantName": "default"},
  {"promptVersion": "2", "promptVariantName": "default"},
 ],
)

この設定で 2 バージョンに均等にトラフィックを分散し、CloudWatch メトリクス(レスポンス品質・レイテンシ・エラー率)を比較評価できます。A-B テストが完了して勝者バージョンが決まったら、エイリアスをそのバージョン単独に更新してトラフィックを集約します。

Converse API での実行

プロンプト ARN を modelId に指定すると、Converse API がプロンプトリソースを自動取得して実行します。変数値は promptVariables で渡します。

import boto3

runtime = boto3.client("bedrock-runtime", region_name="us-east-1")

# エイリアス ARN の形式:
# arn:aws:bedrock:{region}:{account}:prompt/{promptId}:{aliasId}
prompt_arn = (
 f"arn:aws:bedrock:us-east-1:123456789012:prompt/{prompt_id}:{alias_id}"
)

response = runtime.converse(
 modelId=prompt_arn,
 promptVariables={
  "company_name": {"text": "AWS Japan"},
  "customer_query": {"text": "請求書の発行方法を教えてください。"},
 },
)

output = response["output"]["message"]["content"][0]["text"]
print(output)

modelId にプロンプト ARN(エイリアス ARN)を渡すのがポイントです。Bedrock がバックエンドでプロンプトリソースを解決し、定義済みのモデルとパラメータで実行します。呼び出し側はモデル ID や推論パラメータを意識しなくてよいため、アプリケーションコードが大幅にシンプルになります。特定バージョンを直接指定する場合は ARN の末尾をバージョン番号にします(例: ...prompt/{prompt_id}:1)。

InvokeModel での実行

Converse API に対応していないモデルや、詳細なペイロード制御が必要な場合は invoke_model を使います。プロンプト識別子はリクエストボディの promptIdentifier フィールドで渡します。

import json
import boto3

runtime = boto3.client("bedrock-runtime", region_name="us-east-1")

body = json.dumps({
 "promptIdentifier": prompt_arn,
 "promptVariables": {
  "company_name": {"text": "AWS Japan"},
  "customer_query": {"text": "請求書の発行方法を教えてください。"},
 },
})

response = runtime.invoke_model(
 modelId="amazon.nova-pro-v1:0",
 body=body,
 contentType="application/json",
 accept="application/json",
)
result = json.loads(response["body"].read())
print(result["output"]["message"]["content"][0]["text"])

チーム運用のベストプラクティス

大規模チームでの Prompt management 運用では、権限分離と変更管理の設計が重要です。

役割推奨 IAM アクション
プロンプト作成者bedrock:CreatePrompt bedrock:UpdatePrompt
バージョン管理者bedrock:CreatePromptVersion
デプロイ担当bedrock:CreatePromptAlias bedrock:UpdatePromptAlias
閲覧者bedrock:GetPrompt bedrock:ListPrompts

プロンプトの ARN は環境変数か AWS Systems Manager Parameter Store に保存するのが安全です。プロンプトの変更フローは Git と同様の PR レビュープロセスを採用し、マージ後に CI/CD から CreatePromptVersion を自動実行する運用が安定します。本番環境と開発環境でエイリアス名を分け(production / staging)、IAM で書き込み権限を厳格に制御することで誤操作を防げます。Prompt management の変更操作は CloudTrail で記録されるため、誰がいつどのバージョンをデプロイしたかを監査証跡として残せます。


5. Nova Canvas — 画像生成の本番運用

Nova Canvasがテキストプロンプトから画像を生成しinpaintingとoutpaintingと背景除去で編集する画像生成の本番運用フロー
図5: Nova Canvas 画像生成 — 生成・inpainting/outpainting・背景除去

5-1. Nova Canvas の画像生成と編集機能

Amazon Nova Canvas は Bedrock で提供される高品質画像生成モデルです(GA)。テキストプロンプトから画像を生成するだけでなく、inpainting・outpainting・背景除去・カラーガイダンスなどの編集機能を備えており、EC サイトの商品画像や広告クリエイティブを本番運用できます。Nova テキストモデル(Micro/Lite/Pro/Premier)の選定については Vol1 で詳解しているため、本セクションでは Nova Canvas(画像生成 GA モデル)に集中します。

テキストモデル選定の詳細:Bedrock Vol1 を読む

テキストから画像生成(TEXT_IMAGE)

invoke_modelamazon.nova-canvas-v1:0 を指定し、imageGenerationConfig で生成パラメータを設定します。返値は Base64 エンコードされた PNG 画像です。

import boto3
import base64
import json

runtime = boto3.client("bedrock-runtime", region_name="us-east-1")

body = {
 "taskType": "TEXT_IMAGE",
 "textToImageParams": {
  "text": (
"白い背景に置かれた赤いランニングシューズ、"
"プロダクト写真、スタジオ照明、高解像度"
  ),
  "negativeText": "影、テキスト、透かし、ぼかし",
 },
 "imageGenerationConfig": {
  "numberOfImages": 1,
  "height": 1024,
  "width": 1024,
  "cfgScale": 8.0,
  "seed": 42,
 },
}

response = runtime.invoke_model(
 modelId="amazon.nova-canvas-v1:0",
 body=json.dumps(body),
 contentType="application/json",
 accept="application/json",
)

result = json.loads(response["body"].read())
image_b64 = result["images"][0]

with open("output.png", "wb") as f:
 f.write(base64.b64decode(image_b64))
print("画像生成完了: output.png")

cfgScale はプロンプトへの忠実度(1.1 〜 10.0)で、値が高いほど忠実になります。seed を固定するとデバッグ時に再現性が確保できます。本番では seed を省略するかランダム値を使用してバリエーションを生成します。

inpainting — マスク領域の編集

inpainting は画像の特定領域をマスクして再生成する機能です。商品の色変更・不要オブジェクトの除去・テキストの差し替えに使えます。マスク画像は白が「編集対象領域」、黒が「保持領域」を表す 8-bit グレースケール PNG です。

import base64

with open("product_base.png", "rb") as f:
 image_b64 = base64.b64encode(f.read()).decode()

with open("mask.png", "rb") as f:
 mask_b64 = base64.b64encode(f.read()).decode()

body = {
 "taskType": "INPAINTING",
 "inPaintingParams": {
  "image": image_b64,
  "maskImage": mask_b64,
  "text": "青いランニングシューズ、スタジオ照明",
  "negativeText": "影、テキスト",
 },
 "imageGenerationConfig": {
  "numberOfImages": 1,
  "height": 1024,
  "width": 1024,
  "cfgScale": 8.0,
 },
}

response = runtime.invoke_model(
 modelId="amazon.nova-canvas-v1:0",
 body=json.dumps(body),
 contentType="application/json",
 accept="application/json",
)

result = json.loads(response["body"].read())
with open("inpainted.png", "wb") as f:
 f.write(base64.b64decode(result["images"][0]))

マスクのサイズは元画像と同一にする必要があります。マスクが粗いと編集境界が不自然になるため、画像編集ライブラリ(PIL / OpenCV)で精度の高いマスクを準備することが品質向上の鍵です。

outpainting — 画像の拡張

outpainting は既存画像の外側を自然に補完してカンバスを拡張します。縦長の EC 写真を横長のバナー用途に広げる場合などに有効です。

body = {
 "taskType": "OUTPAINTING",
 "outPaintingParams": {
  "image": image_b64,
  "maskImage": mask_b64,
  "text": "白いスタジオ背景、シームレス",
  "outPaintingMode": "DEFAULT",
 },
 "imageGenerationConfig": {
  "numberOfImages": 1,
  "height": 1024,
  "width": 1536,
  "cfgScale": 8.0,
 },
}

outPaintingModeDEFAULT(マスク外を保持)と PRECISE(マスク境界を精密に保持)から選べます。PRECISE は製品輪郭を正確に維持したい EC 用途に適しています。

背景除去(BACKGROUND_REMOVAL)

BACKGROUND_REMOVAL タスクは入力画像から被写体を分離し、背景を透明にした PNG を返します。EC サイトで商品を白背景や任意の背景に合成する前処理として使えます。

body = {
 "taskType": "BACKGROUND_REMOVAL",
 "backgroundRemovalParams": {
  "image": image_b64,
 },
}

response = runtime.invoke_model(
 modelId="amazon.nova-canvas-v1:0",
 body=json.dumps(body),
 contentType="application/json",
 accept="application/json",
)

result = json.loads(response["body"].read())
with open("product_nobg.png", "wb") as f:
 f.write(base64.b64decode(result["images"][0]))

返される画像はアルファチャンネル付き PNG です。numberOfImages は BACKGROUND_REMOVAL では指定不要で、常に1枚が返されます。

画像スタイル制御とプロンプトエンジニアリング

高品質な商品画像を生成するためのプロンプト構成は、「被写体 → 環境 → スタイル → 品質修飾語」の順が効果的です。

要素
被写体赤いランニングシューズ、レザー素材
環境白いスタジオ背景、シームレスグラデーション
スタイルプロダクト写真、商業写真
品質修飾語高解像度、シャープ、ドラマチックな照明

否定プロンプト(negativeText)には 影、テキスト、透かし、ぼかし を入れるとノイズを除去できます。colors パラメータに 16 進数カラーコードを最大 10 色指定することで、生成画像のカラーパレットをブランドガイドラインに合わせられます。


5-2. 画像生成の本番運用(Guardrails 連携)

EC・広告でのユースケース

Nova Canvas の主な本番ユースケースは次のとおりです。

ユースケースタスクポイント
EC 商品ページの背景除去BACKGROUND_REMOVALアルファ PNG → 白背景合成
カラーバリエーション展開INPAINTING精度の高いマスク準備が品質を左右
バナー広告のサイズ拡張OUTPAINTINGアスペクト比の変換
季節キャンペーン画像TEXT_IMAGEブランドカラー指定で統一感
A/B テスト用クリエイティブTEXT_IMAGEseed 固定で差分比較

Guardrails 連携で生成コンテンツを統制する

Nova Canvas の出力に対しても §2 で設定した Guardrails を適用できます。guardrailIdentifierguardrailVersion をリクエストに追加します。

import json
import boto3

runtime = boto3.client("bedrock-runtime", region_name="us-east-1")

body = {
 "taskType": "TEXT_IMAGE",
 "textToImageParams": {
  "text": "製品プロモーション画像、白背景、スタジオ照明",
  "negativeText": "テキスト、透かし",
 },
 "imageGenerationConfig": {
  "numberOfImages": 1,
  "height": 1024,
  "width": 1024,
  "cfgScale": 8.0,
 },
}

response = runtime.invoke_model(
 modelId="amazon.nova-canvas-v1:0",
 body=json.dumps(body),
 contentType="application/json",
 accept="application/json",
 guardrailIdentifier="grd-xxxxxxxxxxxxxxxx",
 guardrailVersion="1",
)

Guardrails はプロンプト(textToImageParams.text)を検査し、ポリシーに違反する場合はリクエストをブロックします。§2 で設定したマルチモーダル対応 Guardrails を使用することで、テキストと画像の両方を統一ポリシーで統制できます。

コスト設計

Nova Canvas は生成リクエスト単位で課金されます(2025 年時点、us-east-1 が主な提供リージョン)。

  • TEXT_IMAGE(1024×1024): 画像 1 枚あたり約 $0.06
  • BACKGROUND_REMOVAL: 画像 1 枚あたり約 $0.01
  • INPAINTING / OUTPAINTING: TEXT_IMAGE と同等

大量バッチ処理では Batch Inference を使うと最大 50% のコスト削減が可能です。バッチジョブは S3 の入力ファイル(JSONL)を読み込み、完了後に S3 へ出力します。解像度を 4096×4096 に上げるとコストは大幅に増加するため、用途別に解像度ティアを設計することを推奨します。プレビュー表示には 512×512、最終成果物には 1024×1024、印刷用途のみ 2048×2048 以上を使う段階的アプローチが効果的です。

S3 + CloudFront での配信設計

生成済み画像を即時配信するには次のパターンが安定します。

  1. Lambda が Bedrock を呼び出して画像を生成する
  2. 生成した PNG を S3 バケットに保存する(s3.put_object
  3. CloudFront ディストリビューションが S3 をオリジンとしてキャッシュ配信する
  4. CloudFront の署名付き URL で期限付きアクセスを制御する

この設計で Lambda の実行時間(最大 15 分)内に収まる生成のみ同期的に処理し、長時間のバッチ生成は Step Functions + Batch Inference を使います。

監視・ログ

CloudWatch Metrics で以下を監視します。

メトリクス閾値の目安対応策
InvokeModelThrottles 急増急増時Exponential Backoff
Lambda Duration画像生成は 10〜30 秒タイムアウトを 60 秒以上に設定
S3 PutObject エラー0 件が目標IAM の s3:PutObject を Lambda ロールに付与

CloudTrail で InvokeModel イベントを記録しておくと、コスト急増時のデバッグに役立ちます。生成リクエストのプロンプトと生成結果を DynamoDB に保存するパターンも、品質改善と監査証跡の両立に効果的です。


6. Nova Reel — 動画生成とマルチモーダル運用

6-1. Nova Reel の動画生成

Amazon Nova Reel は 2025 年に GA(一般提供)となった短尺動画生成モデルです。テキストプロンプトまたは画像を入力として最長 6 秒の動画を生成します。動画生成はリソース集約型の処理であるため、start_async_invoke による非同期実行が基本パターンで、生成結果は Amazon S3 バケットへ出力されます。Nova テキストモデルの詳細な選定基準は Vol1 で扱っているため、本セクションでは Nova Reel(動画生成 GA モデル)の実装と運用設計に集中します。

テキストから動画を生成する(TEXT_VIDEO)

start_async_invoke API を使ってテキストから動画を非同期生成します。呼び出しは即座に invocationArn を返し、実際の生成はバックグラウンドで実行されます。

import json
import time
import boto3

bedrock_runtime = boto3.client("bedrock-runtime", region_name="us-east-1")

OUTPUT_BUCKET = "your-company-nova-reel-output"


def start_video_generation(
 prompt: str,
 job_id: str,
 duration_seconds: int = 6,
) -> str:
 """動画生成ジョブを開始し invocationArn を返す"""
 response = bedrock_runtime.start_async_invoke(
  modelId="amazon.nova-reel-v1:0",
  modelInput={
"taskType": "TEXT_VIDEO",
"textToVideoParams": {
 "text": prompt,
},
"videoGenerationConfig": {
 "durationSeconds": duration_seconds,
 "fps": 24,
 "dimension": "1280x720",
},
  },
  outputDataConfig={
"s3OutputDataConfig": {
 "s3Uri": f"s3://{OUTPUT_BUCKET}/videos/{job_id}/",
}
  },
 )
 job_arn = response["invocationArn"]
 print(f"動画生成ジョブ開始: {job_arn}")
 return job_arn


def wait_for_video(job_arn: str, timeout_seconds: int = 600) -> str | None:
 """ジョブ完了を待機し S3 URI を返す(ポーリング方式)"""
 elapsed = 0
 while elapsed < timeout_seconds:
  status_resp = bedrock_runtime.get_async_invoke(invocationArn=job_arn)
  status = status_resp["status"]
  if status == "Completed":
s3_uri = status_resp["outputDataConfig"]["s3OutputDataConfig"]["s3Uri"]
print(f"生成完了: {s3_uri}")
return s3_uri
  if status in ("Failed", "Cancelled"):
print(f"生成失敗: {status_resp.get('failureMessage', status)}")
return None
  time.sleep(30)
  elapsed += 30
 print(f"タイムアウト: {timeout_seconds} 秒を超過")
 return None

durationSeconds は 1〜6 の整数で指定します(最大 6 秒)。fps は 24fps が標準映像品質です。dimension1280x720(16:9 HD)が一般的で、縦型 SNS 動画には 720x1280 が使えます。

生成にかかる時間は短尺動画でも数分かかることがあります。ポーリング間隔は 30 秒程度が適切で、タイムアウトは少なくとも 10 分(600 秒)を設定します。

画像から動画を生成する(Image-to-Video)

textToVideoParamsimages フィールドに入力画像を含めることで、静止画を起点とした動画を生成できます。EC サイトの商品画像に動きを加えてプロモーション動画に仕上げる用途や、製品デモのアニメーション生成に適しています。

import base64
import boto3

bedrock_runtime = boto3.client("bedrock-runtime", region_name="us-east-1")

with open("product_image.jpg", "rb") as f:
 image_b64 = base64.b64encode(f.read()).decode("utf-8")

response = bedrock_runtime.start_async_invoke(
 modelId="amazon.nova-reel-v1:0",
 modelInput={
  "taskType": "TEXT_VIDEO",
  "textToVideoParams": {
"text": (
 "商品がゆっくり回転しながら光が差し込む、"
 "プロフェッショナルな商品紹介動画、白い背景"
),
"images": [
 {
  "format": "jpeg",
  "source": {"bytes": image_b64},
 }
],
  },
  "videoGenerationConfig": {
"durationSeconds": 6,
"fps": 24,
"dimension": "1280x720",
  },
 },
 outputDataConfig={
  "s3OutputDataConfig": {
"s3Uri": f"s3://{OUTPUT_BUCKET}/videos/product-demo/",
  }
 },
)
job_arn = response["invocationArn"]
print(f"画像→動画 生成ジョブ開始: {job_arn}")

画像入力を使う場合、text でどのような動きや雰囲気を加えるかを具体的に記述するほど意図した動画に近くなります。「カメラがゆっくりズームイン」「左から右へパン移動」「静止カメラ、被写体が回転」のようなカメラワークの指示を含めることが効果的です。

本番向けジョブ管理(DynamoDB + EventBridge パターン)

本番では複数の動画生成ジョブが並行して実行されます。DynamoDB でジョブの状態を管理し、EventBridge Scheduler で定期的なステータス確認 Lambda を実行するアーキテクチャが安定します。

import boto3
from datetime import datetime

dynamodb = boto3.resource("dynamodb")
bedrock_runtime = boto3.client("bedrock-runtime", region_name="us-east-1")


def submit_video_job(
 prompt: str,
 request_id: str,
 bucket: str,
) -> str:
 """動画ジョブを投入し DynamoDB に状態を記録する"""
 response = bedrock_runtime.start_async_invoke(
  modelId="amazon.nova-reel-v1:0",
  modelInput={
"taskType": "TEXT_VIDEO",
"textToVideoParams": {"text": prompt},
"videoGenerationConfig": {
 "durationSeconds": 6,
 "fps": 24,
 "dimension": "1280x720",
},
  },
  outputDataConfig={
"s3OutputDataConfig": {
 "s3Uri": f"s3://{bucket}/videos/{request_id}/",
}
  },
 )
 job_arn = response["invocationArn"]

 table = dynamodb.Table("NovaReelJobs")
 table.put_item(
  Item={
"job_arn": job_arn,
"request_id": request_id,
"prompt": prompt,
"status": "IN_PROGRESS",
"s3_prefix": f"s3://{bucket}/videos/{request_id}/",
"created_at": datetime.utcnow().isoformat(),
  }
 )
 return job_arn


def poll_and_update_job_statuses() -> None:
 """IN_PROGRESS 状態のジョブを一括確認・更新する(Lambda から定期実行)"""
 table = dynamodb.Table("NovaReelJobs")
 bedrock_client = boto3.client("bedrock-runtime", region_name="us-east-1")

 response = table.scan(
  FilterExpression="attribute_exists(job_arn)",
 )
 for item in response.get("Items", []):
  if item["status"] != "IN_PROGRESS":
continue
  status_resp = bedrock_client.get_async_invoke(
invocationArn=item["job_arn"]
  )
  new_status = status_resp["status"]
  if new_status != item["status"]:
table.update_item(
 Key={"job_arn": item["job_arn"]},
 UpdateExpression="SET #s = :status",
 ExpressionAttributeNames={"#s": "status"},
 ExpressionAttributeValues={":status": new_status},
)

EventBridge Scheduler で poll_and_update_job_statuses Lambda を 5 分間隔で実行することで、ジョブ完了を検知して後続処理(SNS 通知・CloudFront 配信パス登録など)を起動できます。

スタイルとペースの制御

Nova Reel の動画品質はプロンプトに含めるカメラワーク・照明・ペース指示によって大きく変わります。

ユースケースプロンプト例動画設定
商品紹介動画「商品が白背景でゆっくり 360 度回転、柔らかなスタジオ照明、プロフェッショナル」6 秒・24fps・1280×720
SNS 広告動画「活気ある都市の朝、コーヒーショップ前のシーン、鮮やかな色彩、縦型フォーマット」6 秒・24fps・720×1280
トレーニング用途「ステップバイステップの作業手順、手のクローズアップ、明確な動作」6 秒・24fps・1280×720
バックグラウンド映像「穏やかな海の波、日没、ループ可能な自然の動き、静止カメラ」6 秒・24fps・1280×720

プロンプトに「ゆっくり(slow motion)」「素早い(fast-paced)」のようなテンポ指示を含めることでペース制御ができます。商業用途では「cinematic」「professional」などのスタイル修飾語を追加することで品質が向上します。

6-2. マルチモーダルコスト最適化

Nova Canvas・Nova Reel・Guardrails・Prompt management を組み合わせた統合コスト管理の設計を解説します。Vol1 の「Nova テキストモデル選定コスト」との差別化として、本セクションは Nova 生成(画像・動画)と Guardrails・Prompt management の統合コスト管理にフォーカスします。テキストモデルのコスト比較については Vol1 を参照してください。

Nova Canvas の料金体系

Nova Canvas は 生成画像 1 枚あたり の料金で課金されます。解像度・品質設定・タスクタイプによって単価が変わります。最新の料金は AWS 料金ページ で確認してください。

コスト最適化の基本は 解像度ティア設計 です。縦横を 2 倍にすると解像度が 4 倍になり、コストも比例して増加します。用途別に解像度を制限し、高解像度生成は承認フローを通じてのみ実行できるよう IAM で制御します。

import json
import boto3

RESOLUTION_TIERS = {
 "preview":  {"width": 512,  "height": 512,  "quality": "standard"},
 "standard": {"width": 1024, "height": 1024, "quality": "standard"},
 "premium":  {"width": 1024, "height": 1024, "quality": "premium"},
 "print": {"width": 2048, "height": 2048, "quality": "premium"},
}


def get_canvas_body(prompt: str, tier: str = "standard") -> str:
 config = RESOLUTION_TIERS.get(tier, RESOLUTION_TIERS["standard"])
 return json.dumps({
  "taskType": "TEXT_IMAGE",
  "textToImageParams": {"text": prompt},
  "imageGenerationConfig": {
"numberOfImages": 1,
"height": config["height"],
"width": config["width"],
"cfgScale": 8.0,
"quality": config["quality"],
  },
 })

大量バッチ処理では Batch Inference(JSONL 入力・S3 出力)を使うとオンデマンド比で最大 50% のコスト削減が可能です。バッチ処理はリアルタイム性が不要なコンテンツ生成(カタログ画像の一括生成など)に適しています。

Nova Reel の料金体系

Nova Reel は 生成動画の秒数 に基づいた料金体系です。最新の単価は AWS 料金ページ で確認してください(推測禁止)。durationSeconds の最適化がコスト管理の基本です。プロモーション用途には 4〜6 秒、SNS クリップには 3 秒など、用途別に必要な秒数を定義することでコストを適切にコントロールできます。

プロビジョンドスループット(Provisioned Throughput) は Nova Canvas および Nova Reel への適用可否を AWS ドキュメント で確認してください。月間の生成ボリュームが安定している場合(EC サイトで月 1,000 枚以上の商品画像を生成するなど)は、オンデマンドよりコストを削減できる可能性があります。

Guardrails の料金体系

Guardrails の料金は以下の要素で構成されます。最新の単価は AWS 料金ページ で確認してください。

課金項目課金単位コスト最適化の方向
テキスト検査1K テキストトークンあたり入力バリデーションで不要な呼び出しを削減
マルチモーダル画像検査画像 1 枚あたり用途別にポリシーを分離(全カテゴリ HIGH は過剰な場合が多い)
Contextual grounding check1K テキストトークンあたり重要な QA ユースケースのみ有効化
Automated Reasoning checkクエリあたり処理コストが高いため利用シーンを厳選

コスト最適化の核は ポリシー分離 です。すべてのアプリで同一 Guardrail を使い回すと、シンプルなテキスト生成にも高コストなマルチモーダル画像検査が走ります。アプリ種別ごとに Guardrail リソースを分離し、必要なポリシーのみを有効化します。

import boto3

bedrock = boto3.client("bedrock", region_name="us-east-1")

# テキストのみのアプリ用: 画像検査なし → 低コスト
text_only_guardrail = bedrock.create_guardrail(
 name="text-only-guardrail-v1",
 contentPolicyConfig={
  "filtersConfig": [
{
 "type": "HATE",
 "inputStrength": "HIGH",
 "outputStrength": "HIGH",
 "inputModalities": ["TEXT"],
 "outputModalities": ["TEXT"],
},
  ]
 },
 blockedInputMessaging="このコンテンツはポリシーに反します。",
 blockedOutputsMessaging="このコンテンツはポリシーに反します。",
)

# マルチモーダルアプリ用: 画像検査を追加 → 画像アプリのみに適用
multimodal_guardrail = bedrock.create_guardrail(
 name="multimodal-guardrail-v1",
 contentPolicyConfig={
  "filtersConfig": [
{
 "type": "HATE",
 "inputStrength": "HIGH",
 "outputStrength": "HIGH",
 "inputModalities": ["TEXT", "IMAGE"],
 "outputModalities": ["TEXT"],
},
  ]
 },
 blockedInputMessaging="このコンテンツはポリシーに反します。",
 blockedOutputsMessaging="このコンテンツはポリシーに反します。",
)

Prompt management の料金体系

Prompt management の料金はプロンプトのストレージ(定義の保存)は無料で、API 呼び出し(GetPromptCreatePromptVersion・Converse 実行)分のみ課金されます。Nova Canvas・Reel と比較してコスト寄与度は軽微です。バージョン数やエイリアス数に上限制限があるため、長期運用では定期的なクリーンアップが必要です。

統合コスト計算と予算アラート

複数コンポーネントを組み合わせた場合のコストを一元管理するには、AWS Cost Explorer のタグベース分析と AWS Budgets のアラートを組み合わせます。

import boto3

budgets = boto3.client("budgets", region_name="us-east-1")


def create_bedrock_budget(
 account_id: str,
 monthly_limit_usd: float,
 alert_email: str,
) -> None:
 """Bedrock の月次予算アラートを作成する"""
 budgets.create_budget(
  AccountId=account_id,
  Budget={
"BudgetName": "bedrock-monthly-limit",
"BudgetLimit": {"Amount": str(monthly_limit_usd), "Unit": "USD"},
"TimeUnit": "MONTHLY",
"BudgetType": "COST",
"CostFilters": {
 "Service": ["Amazon Bedrock"],
},
  },
  NotificationsWithSubscribers=[
{
 "Notification": {
  "NotificationType": "ACTUAL",
  "ComparisonOperator": "GREATER_THAN",
  "Threshold": 80,
  "ThresholdType": "PERCENTAGE",
 },
 "Subscribers": [
  {"SubscriptionType": "EMAIL", "Address": alert_email}
 ],
},
{
 "Notification": {
  "NotificationType": "FORECASTED",
  "ComparisonOperator": "GREATER_THAN",
  "Threshold": 100,
  "ThresholdType": "PERCENTAGE",
 },
 "Subscribers": [
  {"SubscriptionType": "EMAIL", "Address": alert_email}
 ],
},
  ],
 )

CloudWatch カスタムメトリクスで用途別・チーム別の生成件数を記録し、月次の AWS Cost Explorer でプロジェクト別コストを分析します。画像・動画生成ワークフローは短期間でコストが急増しやすいため、月次予算の 80% 到達(実績アラート)と 100% 超過予測(予測アラート)の 2 段階でアラートを設定します。

ROI 測定の設計

Nova Canvas・Reel を本番適用した際の ROI(費用対効果)を定量化するには、生成コストと代替手段のコストを比較します。以下の指標がベースラインとして使われます。

指標測定方法ベンチマーク例
画像 1 枚あたりの生成コストBedrock 料金 ÷ 生成枚数デザイナー外注の 1/10〜1/100 の場合が多い
動画 1 秒あたりの生成コストBedrock 料金 ÷ 合計秒数映像制作外注の 1/50 以下の場合が多い
制作リードタイム削減発注から納品までの時間比較数日〜週 → 秒〜分
修正サイクル改善プロンプト修正の所要時間コードデプロイ不要(Prompt management 併用時)

ROI 測定では「コストの削減額」だけでなく、「速度向上による機会損失の回避(キャンペーン素材の即日制作)」や「パーソナライズ拡張(ユーザー別画像の大量生成)」といった定性的な価値も合わせて評価することで、経営層への説明が容易になります。

Nova Premier(Nova シリーズの上位テキストモデル・複雑推論と蒸留タスク向け)を含む Nova テキストモデル全般の選定基準と費用対効果については、Vol1 で詳解しているため本記事では再掲せず誘導します。

Nova テキストモデルのコスト比較:Bedrock Vol1 を読む


7. 実戦統合パターン — 統制+プロンプト管理+マルチモーダルの本番運用

GuardrailsがリアルタイムにI/O統制しPrompt managementがバージョン管理済みプロンプトを本番に供給しNova CanvasとReelが画像と動画を生成しFlowsがオーケストレーションする実戦統合アーキテクチャ全体図
図6: 実戦統合アーキテクチャ — Guardrails・Prompt management・Nova Canvas/Reel・Flows

7-1. 統制・プロンプト管理・マルチモーダルの統合

本番の生成AIアプリケーションでは、Guardrails(§2-3)・Prompt management(§4)・Nova Canvas/Reel(§5-6)の三要素を組み合わせることで、安全性・品質・マルチモーダル生成を一体的に管理できます。

統合アーキテクチャの全体設計

典型的な企業向けコンテンツ生成システムでは、以下の三層を組み合わせます。

  • 統制層(Guardrails): 入出力の安全性チェック・PII検出・ハルシネーション抑制
  • 管理層(Prompt management): 検証済みプロンプトのバージョン管理・本番デプロイ
  • 生成層(Nova Canvas/Reel): 画像・動画の実際の生成処理

Guardrailsを入力チェック→生成→出力チェックの両端に配置し、Prompt managementでプロンプトをコードから分離します。プロンプトの変更はコードデプロイなしでバージョン切り替えができるため、本番環境での迅速な改善サイクルを実現できます。

import boto3
import json

bedrock = boto3.client("bedrock-runtime", region_name="us-east-1")
bedrock_agent = boto3.client("bedrock-agent", region_name="us-east-1")


def generate_image_with_full_guardrails(
 prompt_id: str,
 prompt_version: str,
 user_input: str,
 guardrail_id: str,
 guardrail_version: str,
) -> dict:
 """Prompt management + Guardrails + Nova Canvas の統合呼び出し例"""

 # Step1: Prompt managementからバージョン管理されたプロンプトを取得
 prompt_resp = bedrock_agent.get_prompt(
  promptIdentifier=prompt_id,
  promptVersion=prompt_version,
 )
 template = prompt_resp["variants"][0]["templateConfiguration"]["text"]["text"]
 final_prompt = template.replace("{{user_input}}", user_input)

 # Step2: Guardrailsで入力を事前検査
 input_check = bedrock.apply_guardrail(
  guardrailIdentifier=guardrail_id,
  guardrailVersion=guardrail_version,
  source="INPUT",
  content=[{"text": {"text": final_prompt}}],
 )
 if input_check["action"] == "GUARDRAIL_INTERVENED":
  return {
"status": "blocked",
"reason": input_check["outputs"][0]["text"],
  }

 # Step3: Nova Canvasで画像生成
 body = json.dumps({
  "taskType": "TEXT_IMAGE",
  "textToImageParams": {"text": final_prompt},
  "imageGenerationConfig": {
"numberOfImages": 1,
"height": 1024,
"width": 1024,
"cfgScale": 8.0,
  },
 })
 response = bedrock.invoke_model(
  modelId="amazon.nova-canvas-v1:0",
  body=body,
 )
 result = json.loads(response["body"].read())

 # Step4: Guardrailsで出力(プロンプト内容)を事後検査
 output_check = bedrock.apply_guardrail(
  guardrailIdentifier=guardrail_id,
  guardrailVersion=guardrail_version,
  source="OUTPUT",
  content=[{"text": {"text": final_prompt}}],
 )
 if output_check["action"] == "GUARDRAIL_INTERVENED":
  return {"status": "output_blocked", "reason": "生成物が統制ポリシーに抵触しました"}

 return {
  "status": "success",
  "image_base64": result["images"][0],
  "prompt_id": prompt_id,
  "prompt_version": prompt_version,
 }

複数サービス統合時のコスト設計

Guardrails・Prompt management・Nova Canvas/Reelを組み合わせる場合、コストは以下の要素で構成されます。

コスト要素課金対象注意点
Guardrails検査テキスト1K tokenあたり入出力それぞれ課金
Nova Canvas生成解像度・枚数で変動高解像度は急騰
Nova Reel生成秒数・品質で変動非同期ジョブ別途管理
Prompt managementAPI呼び出し分のみストレージは無料

コスト制御の核心は、Guardrailsで入力を拒否してから生成処理に進む設計です。入力段階で遮断することで、不要な画像・動画生成コストを抑制できます。本番では、入力Guardrailsのレイテンシ(通常50〜200ms)を計上した上でタイムアウト設計をします。

マルチモーダル統合のエラーハンドリング

Guardrails遮断はリトライ対象外ですが、Nova Canvasの一時的なスロットリングはリトライで回復できます。

import time
from botocore.exceptions import ClientError


def invoke_model_with_retry(client, model_id: str, body: str, max_retries: int = 3) -> dict:
 """Nova Canvas/Reelのスロットリング対応リトライ"""
 for attempt in range(max_retries):
  try:
return client.invoke_model(modelId=model_id, body=body)
  except ClientError as e:
code = e.response["Error"]["Code"]
if code == "ThrottlingException" and attempt < max_retries - 1:
 time.sleep(2 ** attempt)  # 指数バックオフ: 1s, 2s, 4s
 continue
raise
 raise RuntimeError(f"{model_id}: 最大リトライ({max_retries}回)に達しました")

Guardrails遮断時はユーザーへの適切なフィードバック(拒否理由の要約)を返し、リトライ誘導はしないようにします。遮断ログをCloudWatch Logsに送信することで、誤遮断率をモニタリングできます。

7-2. Vol1(Flows/評価)との連携設計

Vol3の統制・プロンプト管理・マルチモーダル生成は、Vol1のFlows・Evaluationsと組み合わせることで、より高度な本番システムを構築できます。Flowsの基礎設計とLLM-as-Judgeの詳細はVol1を参照してください。

Flows + Guardrails + Prompt managementの連携

Bedrock Flowsオーケストレーションにおいて、各ノードにGuardrailsとPrompt managementを組み合わせる設計では、プロンプトノードのARNをPrompt managementで管理し、Flowsのnode設定でGuardrailsを有効化します。

# FlowsのPromptノードにGuardrailsとPrompt managementを統合する定義例
prompt_node_config = {
 "name": "ContentGenerationNode",
 "type": "Prompt",
 "configuration": {
  "prompt": {
"sourceConfiguration": {
 "resource": {
  # Prompt managementで管理されたARNを直接参照
  "promptArn": "arn:aws:bedrock:us-east-1:123456789012:prompt/ABCDEF12/1"
 }
},
"guardrailConfiguration": {
 "guardrailIdentifier": "grd-xxxxxxxx",
 "guardrailVersion": "1",
},
  }
 },
}

FlowsのConditionノードでGuardrail評価結果を分岐し、安全な入力のみ次ノードに進む設計が効果的です。プロンプトはPrompt managementのARNで参照するため、Flow定義を変えずにプロンプト内容を更新できます。

Evaluations(LLM-as-Judge)とGuardrailsの役割分担

品質担保の観点では、EvaluationsとGuardrailsは相補的な役割を果たします。

機能GuardrailsEvaluations(LLM-as-Judge)
実行タイミングリアルタイム(同期)バッチ評価(非同期)
対象領域安全性・コンプライアンス品質・事実整合・有用性
判断根拠ルール/ポリシーベースLLMによる評価
コスト構造検査ごと課金評価実行時のみ課金

本番運用では、リアルタイムのGuardrailsで安全性を確保し、定期的なEvaluationsで品質トレンドを監視する二段階品質管理が効果的です。Evaluationsの結果をPrompt managementのバージョン選択判断に活用するループを組むことで、品質改善サイクルが自動化されます。

ガバナンス体制の設計

本番生成AIアプリのガバナンスは、技術的な統制だけでなく運用体制も含めて設計します。

  • Guardrailsポリシー管理: セキュリティチームがGuardrail設定を管理・レビュー
  • Prompt management権限: 本番バージョンへのデプロイ権限をCI/CDパイプラインに限定
  • Nova生成ログ: CloudTrailとCloudWatch Logsで全生成リクエストを監査証跡として保存
  • 定期レビュー: Guardrailsの誤遮断率・Evaluationsの品質スコアを週次でレビュー

CloudTrailではBedrockのInvokeModelイベントが記録されるため、誰が・いつ・どのモデルで生成したかを事後監査できます。GuardrailsのメトリクスはCloudWatch Metrics AWS/Bedrock 名前空間で確認できます。

Flows・評価の深掘り:Bedrock Vol1 を読む


8. 詰まりポイント・アンチパターン・まとめ

8-1. 詰まりポイント(9 選)

本番運用で遭遇しやすいGuardrails・Prompt management・Nova Canvas/Reelの詰まりポイントを解説します。

詰まり① 画像フィルタのしきい値が過剰で正常コンテンツを誤遮断する

Guardrailsのコンテンツフィルタはしきい値をHIGHに設定すると、マーケティング用の広告画像など業務上必要なコンテンツも遮断してしまいます。最初はMEDIUM付近で運用を開始し、CloudWatch MetricsのInvokedCountGuardrailInvokedCountを比較して誤遮断率を測定しながら調整するのが正攻法です。本番デプロイ前に代表的なプロダクション入力100件でA/Bテストすることを強くお勧めします。

詰まり② Automated Reasoningのポリシー定義が曖昧で検証精度が低い

自然言語でポリシーを記述するAutomated Reasoning checksでは、「在庫のある製品のみ推奨する」のように具体的かつ機械検証可能な形式で記述する必要があります。「適切なコンテンツのみ生成する」のような曖昧な表現は検証ロジックが定まらず、精度が大幅に低下します。ポリシー設計後は必ず検証用データセット(正解例・不正解例各20件以上)でドライラン評価を実施します。

詰まり③ Prompt versionの本番取り違え

Prompt managementではバージョン番号(1、2、3…)とエイリアス(DRAFT、PRODなど)を使い分けられますが、コードにバージョン番号を直書きすると新バージョンリリース時に古いバージョンを参照し続けるトラブルが発生します。本番は常にエイリアスPRODを参照し、リリース時にエイリアスを付け替える運用にします。

import boto3

bedrock_agent = boto3.client("bedrock-agent", region_name="us-east-1")

# NG: バージョン番号の直書き
# prompt_version = "3"  # リリース後に古いバージョンを参照し続けるリスク

# OK: エイリアスを参照(コードを変えずにプロンプトを切り替えられる)
prompt_version = "PROD"
bedrock_agent.get_prompt(
 promptIdentifier="ABCDEF12",
 promptVersion=prompt_version,  # "PROD" or "DRAFT" で安全に切り替え
)

詰まり④ Nova Canvasの高解像度生成によるコスト急増

デフォルトの1024×1024から4096×4096に解像度を変更すると、生成コストが16倍近くになります。本番では用途別に解像度ティアを設計し、プレビュー表示には512×512、最終成果物には1024×1024、印刷用途のみ2048×2048以上を使う段階的アプローチが効果的です。Guardrailsの検査は解像度に関係なく課金されるため、解像度が上がるとトータルコストは生成費用+検査費用で積み上がります。

詰まり⑤ Nova Reelの非同期ジョブ管理の複雑さ

Nova Reelの動画生成は非同期ジョブ(StartAsyncInvoke)で実行されます。ジョブIDの管理と完了待ちのポーリングを実装しないと、生成結果を取得できません。DynamoDBでジョブIDとリクエスト情報を管理し、完了通知にEventBridgeまたはSQSを使う設計が本番では安定します。

import boto3

bedrock_async = boto3.client("bedrock-runtime", region_name="us-east-1")
dynamodb = boto3.resource("dynamodb")

start_resp = bedrock_async.start_async_invoke(
 modelId="amazon.nova-reel-v1:0",
 modelInput={
  "taskType": "TEXT_VIDEO",
  "textToVideoParams": {"text": "商品紹介動画のプロンプトテキスト"},
  "videoGenerationConfig": {"durationSeconds": 6, "fps": 24},
 },
 outputDataConfig={
  "s3OutputDataConfig": {"s3Uri": "s3://your-bucket/nova-reel-output/"}
 },
)
job_arn = start_resp["invocationArn"]
# DynamoDBにジョブIDを保存(後でステータス確認に使用)
table = dynamodb.Table("VideoGenerationJobs")
table.put_item(Item={"job_arn": job_arn, "status": "IN_PROGRESS"})

詰まり⑥ Guardrails未適用の生成エンドポイントが残存する

マイクロサービス構成や段階的移行の過程で、一部のエンドポイントにGuardrails設定を付け忘れたまま本番稼働するケースがあります。新規エンドポイント追加時のチェックリストにGuardrails設定の確認を含め、チームのコードレビューで必須化します。AWS Configルールでモデル呼び出しにGuardrailsが設定されているかを自動検査する仕組みを整備すると効果的です。

詰まり⑦ マルチモーダルでのPII漏れ

テキストGuardrailsを設定していても、画像埋め込みテキストはデフォルトでPIIスキャン対象外になる場合があります。マルチモーダル画像フィルタのPII検出オプションを明示的に有効化し、医療書類や個人情報が含まれる可能性のある画像入力には必ず適用します。

詰まり⑧ Prompt managementの変数未解決エラー

プロンプトテンプレートに変数を定義していても、実行時に変数マッピングを渡さないとUNRESOLVED_VARIABLEエラーが発生します。Converseでの実行時にはpromptVariablesパラメータで変数を渡す必要があります。

import boto3

bedrock = boto3.client("bedrock-runtime", region_name="us-east-1")

# Converseでのプロンプト変数渡し(promptVariablesが必須)
response = bedrock.converse(
 modelId="amazon.nova-pro-v1:0",
 promptVariables={
  "user_input": {"text": "ユーザーの実際の入力内容をここに設定"}
 },
 system=[{"text": "arn:aws:bedrock:us-east-1:123456789012:prompt/ABCDEF12"}],
 messages=[{"role": "user", "content": [{"text": "{{user_input}}"}]}],
)

詰まり⑨ Contextual groundingの閾値調整不足による偽陽性・偽陰性

Contextual grounding checkのgroundedness(根拠整合性)とrelevance(関連性)のしきい値はデフォルト0.7ですが、ドメイン固有の用語や要約タスクでは偽陽性(正しい回答を不正解判定)が増加します。最初は0.5付近から始め、評価データセットでF1スコアを計測しながら調整します。しきい値を下げすぎるとハルシネーションを見逃すため、ビジネス要件に応じた最適値を探ります。

8-2. アンチパターン → 正解変換(6 選)

本番運用でよく見られるアンチパターンとその改善策を整理します。

アンチパターン① Guardrailsを後付けで追加する

アンチパターン: まず機能を実装して、後でGuardrailsを追加しようとする。

問題点: 後付けでGuardrailsを追加すると、既存のプロンプト設計がGuardrailsのルールと衝突し、大量の誤遮断が発生します。リファクタリングコストが膨大になります。

正解: 設計段階からGuardrailsのコンテンツポリシー・PIIポリシー・denied topicsを定義し、プロンプト設計とGuardrails設定を同時に進めます。ユニットテストにGuardrailsの入出力検査を含め、CI/CDパイプラインで自動検証します。

アンチパターン② プロンプトをコードにハードコードする

アンチパターン: プロンプト文字列をPythonファイルやLambda関数に直接書き込む。

問題点: プロンプト改善のたびにコードデプロイが必要になり、リリースサイクルが長くなります。A/Bテストも困難です。

正解: Prompt managementでプロンプトを管理し、コードからはARNまたはIDで参照します。本番/検証のバージョン切り替えはエイリアスで行い、コードは変更しません。プロンプト改善をデータサイエンティストがコードレビューなしで実行できる体制になります。

アンチパターン③ 画像・動画を統制なしで生成する

アンチパターン: Nova Canvas/ReelをGuardrails未適用で本番公開する。

問題点: 不適切なコンテンツ・著作権侵害・PII混入の画像/動画の生成・公開リスクがあります。企業のブランドイメージ損傷や法的リスクにもつながります。

正解: 全ての生成リクエストでGuardrailsを事前検査し、Nova Canvas/Reelのinvoke_modelguardrailConfigを渡します。画像フィルタはHATE/VIOLENCE/SEXUALカテゴリを最低MEDIUMに設定します。生成後は出力も検査し、問題のある生成物は配信しません。

アンチパターン④ 全リクエストにAutomated Reasoningを適用する

アンチパターン: コスト・パフォーマンスを考慮せず、全リクエストへAutomated Reasoning checksを適用する。

問題点: Automated Reasoningは高精度ですが処理時間(数百ms〜数秒)とコストが高く、チャットのような低レイテンシ要件のユースケースでは非現実的です。

正解: Automated Reasoningは事実確認が特に重要なユースケース(医療・金融・法令)に絞って適用します。一般的なコンテンツ生成にはContextual groundingで対応し、Automated Reasoningはティアリングで段階的に適用します。

アンチパターン⑤ Nova Canvasの生成結果を検証なしで配信する

アンチパターン: Nova Canvasで生成した画像をそのままCDNやS3パブリックバケットに配信する。

問題点: Guardrailsの出力チェックをバイパスする設計になっているため、フィルタリング漏れが本番ユーザーに届きます。特に大量バッチ生成のケースでリスクが高まります。

正解: 生成→出力チェック→配信の順に処理し、出力チェックでGuardrailが介入した場合は配信をキャンセルしてエラーログを記録します。生成物はS3プライベートバケットに一時保存し、検証通過後にのみ公開バケットへコピーします。

アンチパターン⑥ Prompt versionをコードに直書きしてデプロイごとに更新する

アンチパターン: prompt_version = "5" のようにバージョン番号をコードに書き、新バージョンリリースのたびにコードも更新する。

問題点: プロンプト改善とコードデプロイが結合してしまい、緊急のプロンプト修正にもデプロイ承認フローが必要になります。深夜の障害対応でプロンプト修正が遅延するリスクもあります。

正解: コードは常にエイリアス(PROD)を参照し、リリース時はPrompt managementのエイリアスを付け替えるだけにします。コードデプロイなしで即座にプロンプトを切り替えられ、ロールバックも容易になります。

8-3. 本番運用の監視チェックリスト

Vol3で扱ったコンポーネントを本番運用する際に確認すべき監視項目を整理します。定期的にこのチェックリストを確認することで、統制・品質・マルチモーダル生成の健全性を維持できます。

Guardrails監視

監視項目確認頻度確認方法
誤遮断率(正常コンテンツの遮断比率)日次CloudWatch Metrics
PII検出件数の推移週次CloudWatch Logs Insights
Contextual grounding偽陽性率週次カスタムメトリクス
Automated Reasoning精度月次評価データセットで定期検証

Prompt management監視

  • 本番エイリアスが意図したバージョンを指しているかを定期確認
  • プロンプトバージョン変更後の品質スコア(Evaluationsで計測)の比較
  • CreatePromptVersionイベントをCloudTrailで監査

Nova Canvas/Reel監視

  • 月次コストレポートで解像度別・モデル別の費用内訳を確認
  • Nova Reelジョブの完了率・タイムアウト率を日次でモニタリング
  • S3出力バケットのストレージコストと生成物の保持期間を管理
import boto3

cw = boto3.client("cloudwatch", region_name="us-east-1")

# Guardrailsの介入率をカスタムメトリクスとして記録
def record_guardrail_metrics(total_requests: int, intervened: int, guardrail_id: str):
 cw.put_metric_data(
  Namespace="BedrockApp/Guardrails",
  MetricData=[
{
 "MetricName": "InterventionRate",
 "Dimensions": [{"Name": "GuardrailId", "Value": guardrail_id}],
 "Value": intervened / total_requests if total_requests > 0 else 0,
 "Unit": "None",
}
  ],
 )

CloudWatchアラームで介入率が5%を超えたらSNS通知を送り、しきい値の見直しトリガーとする運用が効果的です。

8-4. まとめと Vol4 予告

本記事では、Amazon Bedrockを使った本番生成AIアプリケーションの「統制・品質・マルチモーダル」の三要素を解説しました。

Vol3で習得した主要スキルは以下のとおりです。

  • Guardrails高度化: マルチモーダル画像フィルタ(GA 2025-03)・denied topics・PII保護・Contextual grounding・Automated Reasoning checksの実装と本番設計
  • Prompt management: プロンプトのバージョン管理・本番デプロイ・エイリアス運用・Converse/InvokeModelでの識別子実行
  • Nova Canvas: 画像生成(TEXT_IMAGE)・inpainting/outpainting・背景除去・Guardrails連携によるコンテンツ統制
  • Nova Reel: 非同期動画生成(StartAsyncInvoke)・スタイル/ペース制御・S3連携・ジョブ管理設計
  • 実戦統合: Guardrails+Prompt management+Nova Canvas/Reel+Flows(Vol1)を組み合わせた本番アーキテクチャ

これらの要素を組み合わせることで、安全性・品質・マルチモーダル生成を一体的に管理する本番グレードの生成AIシステムを構築できます。Guardrailsを設計の中心に置き、Prompt managementでプロンプトのライフサイクルを管理し、Nova Canvas/Reelでリッチなマルチモーダルコンテンツを生成する三位一体のアーキテクチャが、Bedrockを使った本番システムの標準的な構成となります。

Vol4予告: 次巻ではBedrock AgentCoreを中心に、エージェントのランタイム管理・永続メモリ・マルチエージェント協調・本番エージェントのガバナンス設計を取り上げる予定です。複数の専門エージェントが協調して複雑なタスクを処理するマルチエージェントアーキテクチャの実装パターンを解説します。今回習得したGuardrailsとPrompt managementはAgentCoreとも直接統合できるため、Vol3の知識がそのままVol4の基盤となります。

Bedrock 本番運用シリーズ — 全巻ナビゲーション

  • Vol1: Flows・Evaluations(LLM-as-Judge)・Nova モデル選定Bedrock Vol1 を読む
  • Vol2: Amazon Q連携・Data Automation・カスタムモデルBedrock Vol2 を読む
  • Vol3: Guardrails高度化・Prompt management・Nova Canvas/Reel → 本記事

関連:Bedrock Vol2(Q連携・カスタムモデル)を読む