View a markdown version of this page

구성 번들을 사용하여 A/B 테스트 실행 - Amazon Bedrock AgentCore

구성 번들을 사용하여 A/B 테스트 실행

테스트하는 변경 사항이 다른 시스템 프롬프트, 다른 모델 ID 또는 다른 도구 설명과 같은 순전히 구성인 경우 구성 번들 패턴을 사용합니다. 두 변형 모두 서로 다른 구성 번들 버전으로 동일한 AgentCore 런타임에서 실행됩니다. AgentCore Gateway는 W3C 파티커 헤더를 통해 각 요청에 올바른 번들 참조를 주입하고 에이전트는 런타임에 이를 읽습니다. 즉, AgentCore 런타임 하나와 온라인 평가 구성 하나를 배포합니다.

구성 번들 A/B 테스트를 위한 키 구성:

  • 변형 구성: 번들 ARN 및 버전 variantConfiguration.configurationBundle 사용

  • 평가 구성: 단일 공유 onlineEvaluationConfigArn

테스트 중인 변경에 코드 변경, 프레임워크 업그레이드 또는 완전히 다른 에이전트 구현이 포함된 경우 대신 대상 기반 라우팅을 사용합니다. 대상 기반 라우팅을 사용하여 A/B 테스트 실행을 참조하세요.

이 연습에서는 고객 지원 에이전트를 예로 사용합니다. 에이전트는 주문 조회, 반품 및 할인 요청을 처리합니다. 에이전트를 배포하고, 서로 다른 시스템 프롬프트(제어 및 처리)로 구성 번들 2개를 생성하고, A/B 테스트를 생성하고, 트래픽을 전송하고, 결과를 검토하고, 승자를 배포합니다.

1단계: 프로젝트 생성

AgentCore CLI를 사용하여 프로젝트를 생성합니다.

agentcore create --name ABTestConfigBased --no-agent cd ABTestConfigBased

2단계: 런타임 추가

에이전트 런타임을 추가합니다.

agentcore add agent \ --name csAgent \ --language Python \ --framework Strands \ --model-provider Bedrock \ --memory none \ --build CodeZip

프로젝트 구조:

ABTestConfigBased/
├── agentcore/
│   ├── agentcore.json      # Project and resource configuration
│   ├── aws-targets.json    # Deployment target (account and region)
│   └── cdk/                # CDK infrastructure (auto-managed)
└── app/
    └── csAgent/
        ├── main.py         # Agent entrypoint
        └── pyproject.toml  # Python dependencies

3단계: 에이전트 코드 업데이트 및 배포

를 다음과 app/csAgent/main.py 같이 바꿉니다. 키 추가는 런타임 시 활성 구성 번들을 읽는 BeforeModelCallEvent 후크입니다.

"""Customer support agent with configuration bundle integration.""" from strands import Agent, tool from strands.models.bedrock import BedrockModel from strands.hooks.events import BeforeModelCallEvent from bedrock_agentcore.runtime import BedrockAgentCoreApp, BedrockAgentCoreContext app = BedrockAgentCoreApp() DEFAULT_MODEL_ID = "global.anthropic.claude-sonnet-4-5-20250929-v1:0" DEFAULT_SYSTEM_PROMPT = "You are a helpful customer support assistant." @tool def lookup_order(order_id: str) -> str: """Look up an order by ID.""" orders = { "ORD-1001": {"status": "delivered", "item": "Blue T-Shirt", "total": "$29.99"}, "ORD-1002": {"status": "in_transit", "item": "Running Shoes", "est_delivery": "2026-04-05"}, "ORD-1003": {"status": "delayed", "item": "Wireless Headphones", "days_late": 5}, } return str(orders.get(order_id, {"error": f"Order {order_id} not found"})) @tool def initiate_return(order_id: str, reason: str) -> str: """Initiate a return for an order.""" return f"Return initiated for {order_id}. Reason: {reason}. Return label sent to customer email." @tool def apply_discount(order_id: str, discount_percent: int, reason: str) -> str: """Apply a discount to an order.""" return f"Applied {discount_percent}% discount to {order_id}. Reason: {reason}." def dynamic_config_hook(event: BeforeModelCallEvent): """Read config bundle and apply system prompt before every model call.""" config = BedrockAgentCoreContext.get_config_bundle() event.agent.system_prompt = config.get("system_prompt", DEFAULT_SYSTEM_PROMPT) agent = Agent( model=BedrockModel(model_id=DEFAULT_MODEL_ID), tools=[lookup_order, initiate_return, apply_discount], system_prompt=DEFAULT_SYSTEM_PROMPT, ) agent.hooks.add_callback(BeforeModelCallEvent, dynamic_config_hook) @app.entrypoint def invoke(payload, context): result = agent(payload.get("prompt", "Hello")) return {"response": result.message["content"][0]["text"]} if __name__ == "__main__": app.run()

app/csAgent/pyproject.toml 종속성 업데이트:

dependencies = [ "aws-opentelemetry-distro", "bedrock-agentcore >= 1.8.0", "boto3", "botocore[crt] >= 1.35.0", "strands-agents[otel] >= 1.13.0", "opentelemetry-distro", "opentelemetry-instrumentation", ]

고객 지원 에이전트를 AgentCore 런타임에 배포합니다.

agentcore deploy

배포 후 출력의 런타임 ARN을 기록해 둡니다(예: arn:aws:bedrock-agentcore:us-west-2:123456789012:runtime/csAgent-abc123). 구성 번들을 생성하는 데 필요합니다.

에이전트가 실행 중인지 확인합니다.

agentcore invoke --prompt "What is the status of order ORD-1003?"

BeforeModelCallEvent 후크는 각 LLM 호출 전에 실행되어 요청 컨텍스트에서 활성 구성 번들을 읽습니다. A/B 테스트 중에 AgentCore Gateway는 각 세션을 변형에 할당하고 W3C 수수료 헤더를 통해 해당 번들 참조를 전파합니다. 런타임을 사용하면를 통해이 기능을 사용할 수 있으므로 제어 세션은 번들 v1BedrockAgentCoreContext을 수신하고 처리 세션은 번들 v2를 수신합니다. 에이전트는 수신하는 번들에 있는 시스템 프롬프트를 적용합니다.

자세한 내용은 런타임 시 구성 번들 사용을 참조하세요.

4단계: 구성 번들 생성

두 개의 구성 번들을 생성합니다. 하나는 제어용(현재 프롬프트)이고 다른 하나는 처리용(최적화된 프롬프트)입니다. A/B 테스트는 이들 간에 트래픽을 분할하여 어떤 프롬프트가 더 나은 평가자 점수를 산출하는지 측정합니다.

컨트롤 번들 - 현재 시스템 프롬프트:

agentcore add config-bundle \ --name customerSupportControl \ --components '{ "arn:aws:bedrock-agentcore:us-west-2:123456789012:runtime/csAgent-abc123": { "configuration": { "system_prompt": "You are a helpful customer support assistant for Acme Store." } } }' agentcore deploy

처리 번들 - 에이전트가 보다 선제적으로 행동하도록 지시하는 최적화된 시스템 프롬프트입니다.

agentcore add config-bundle \ --name customerSupportTreatment \ --components '{ "arn:aws:bedrock-agentcore:us-west-2:123456789012:runtime/csAgent-abc123": { "configuration": { "system_prompt": "You are a customer support assistant for Acme Store. Be proactive: check order status before the customer asks, offer discounts for delayed orders, and summarize actions taken at the end of each response." } } }' agentcore deploy

각 배포 후 출력에서 번들 ARN 및 버전 ID를 기록해 둡니다. A/B 테스트를 생성할 때 필요합니다.

5단계: 온라인 평가 구성 생성

A/B 테스트에는 두 변형 모두에서 세션을 채점하기 위한 온라인 평가 구성이 필요합니다. 온라인 평가는 실시간 트래픽에 대해 평가자를 실행하고 A/B 테스트의 통계 엔진에 점수를 제공합니다.

구성 번들 변형의 경우 공유 AgentCore 런타임을 모니터링하는 단일 온라인 평가 구성을 생성합니다.

agentcore add online-eval \ --name customerSupportEval \ --runtime csAgent \ --evaluator "Builtin.Helpfulness" \ --sampling-rate 100.0 \ --enable-on-create agentcore deploy

배포 후 출력의 온라인 평가 구성 ARN을 기록해 둡니다. A/B 테스트를 생성할 때 필요합니다.

작은 정보

모든 세션이 평가되고 결과가 통계적 유의성에 더 빨리 도달하도록 A/B 테스트 --sampling-rate 100.0 중에를 설정합니다. 테스트가 종료된 후 속도를 낮출 수 있습니다.

평가자 옵션 및 구성에 대한 자세한 내용은 온라인 평가 생성을 참조하세요.

6단계: 게이트웨이 및 대상 생성

config-bundle A/B 테스트는 AgentCore Gateway를 통해 트래픽을 라우팅하므로 테스트를 시작하기 전에 게이트웨이와 해당 대상이 이미 배포되어 있어야 합니다. 런타임을 http-runtime 대상으로 하는 게이트웨이를 추가한 다음 배포합니다.

agentcore add gateway --name csGateway agentcore add gateway-target \ --name customer-support \ --gateway csGateway \ --type http-runtime \ --runtime csAgent agentcore deploy

7단계: A/B 테스트 생성

제어 프롬프트와 처리 프롬프트 간에 트래픽을 80/20으로 분할하는 A/B 테스트를 생성합니다. 두 변형 모두 동일한 AgentCore 런타임에서 구성 번들을 참조하고 점수를 매기기 위한 단일 온라인 평가 구성을 공유합니다.

AgentCore CLI
agentcore run ab-test \ --mode config-bundle \ --name customerSupportPromptTest \ --gateway csGateway \ --runtime csAgent \ --control-bundle customerSupportControl \ --control-version <control-bundle-version-id> \ --treatment-bundle customerSupportTreatment \ --treatment-version <treatment-bundle-version-id> \ --online-eval customerSupportEval \ --control-weight 80 \ --treatment-weight 20

agentcore run ab-test는 서비스에서 A/B 테스트 작업을 시작합니다. 명령이 반환되는 즉시 테스트가 실행 중입니다. --disable-on-create를 전달하여 중지된 파일을 생성합니다. 작업을 검토하려면를 실행agentcore view ab-test <id>하거나 아래의 작업 JSON을 살펴봅니다.cli/jobs/ab-tests/. --gateway 플래그는 필수이며 6단계에서 배포한 게이트웨이를 참조해야 합니다. 게이트웨이당 한 번에 하나의 테스트만 실행 중일 수 있습니다. 명령은에서 id 필드--json로도 사용할 수 있는 테스트의 작업 ID를 인쇄합니다. 아래 수명 주기 명령에는이 ID가 필요합니다.

참고

--control-version--treatment-version 값은 3단계에서 구성 번들을 배포할 때 반환되는 버전 IDs입니다.

AWS SDK (boto3)
import boto3 import uuid client = boto3.client("bedrock-agentcore", region_name="us-west-2") response = client.create_ab_test( name="customerSupportPromptTest", gatewayArn="arn:aws:bedrock-agentcore:us-west-2:123456789012:gateway/gw-abc123", roleArn="arn:aws:iam::123456789012:role/ABTestRole", evaluationConfig={ "onlineEvaluationConfigArn": "arn:aws:bedrock-agentcore:us-west-2:123456789012:online-evaluation-config/eval-abc123" }, variants=[ { "name": "C", "weight": 80, "variantConfiguration": { "configurationBundle": { "bundleArn": "arn:aws:bedrock-agentcore:us-west-2:123456789012:configuration-bundle/customerSupportControl-Ab1Cd2Ef3G", "bundleVersion": "12345678-1234-1234-1234-123456789012" } } }, { "name": "T1", "weight": 20, "variantConfiguration": { "configurationBundle": { "bundleArn": "arn:aws:bedrock-agentcore:us-west-2:123456789012:configuration-bundle/customerSupportTreatment-Ab1Cd2Ef3G", "bundleVersion": "12345678-1234-5678-9abc-123456789012" } } } ], enableOnCreate=True, clientToken=str(uuid.uuid4()), ) ab_test_id = response["abTestId"] print(f"Created A/B test: {ab_test_id}") print(f"Status: {response['status']}") print(f"Execution status: {response['executionStatus']}")

8단계: AgentCore 게이트웨이를 통해 트래픽 전송

A/B 테스트를 실행한 후 AgentCore Gateway HTTP 엔드포인트를 통해 트래픽을 전송합니다. AgentCore Gateway는 런타임 세션 ID를 기반으로 변형(제어 또는 처리)에 각 요청을 할당합니다.

변형 할당 작동 방식

AgentCore Gateway는 X-Amzn-Bedrock-AgentCore-Runtime-Session-Id 헤더를 사용하여 제공할 구성 번들 변형을 결정합니다. 이 헤더는 선택 사항입니다. 제공하지 않으면 런타임이 세션 ID를 자동으로 생성합니다. 그런 다음 AgentCore Gateway는 세션 ID(제공했는지 또는 런타임에서 생성했는지 여부)를 사용하여 구성된 트래픽 가중치를 기반으로 변형에 요청을 할당합니다.

세션 할당은 고정됩니다. 세션 ID가 변형에 할당되면 동일한 세션 ID를 가진 모든 후속 요청이 동일한 변형으로 라우팅됩니다. 이렇게 하면 트래픽 분할에 따라 변형 간에 새 세션을 분산하면서 세션 내에서 일관된 경험을 보장할 수 있습니다.

테스트를 위한 트래픽 생성

다음 스크립트를 로 저장하여 <gateway-id><target-name>를 배포 출력의 값으로 loadgen.sh바꿉니다.

#!/bin/bash export AWS_ACCESS_KEY_ID=$(aws configure get aws_access_key_id) export AWS_SECRET_ACCESS_KEY=$(aws configure get aws_secret_access_key) export AWS_SESSION_TOKEN=$(aws configure get aws_session_token) GATEWAY_URL="https://<gateway-id>.gateway.bedrock-agentcore.us-west-2.amazonaws.com/<target-name>/invocations" PROMPTS=( "What is the status of order ORD-1003?" "I want to return order ORD-1001, it doesn't fit." "My order ORD-1003 is late. Can I get a discount?" "Where is my order ORD-1002?" "I need help with a return for order ORD-1001. The color is wrong." "Can you check on order ORD-1003? I've been waiting forever." "I'd like to cancel order ORD-1002 if it hasn't shipped yet." "Order ORD-1003 is delayed again. This is unacceptable." "What's your return policy for order ORD-1001?" "My headphones order ORD-1003 still hasn't arrived. What can you do?" ) for i in $(seq 1 30); do PROMPT="${PROMPTS[$(( (i - 1) % ${#PROMPTS[@]} ))]}" echo "=== Request $i: $PROMPT ===" curl -s --aws-sigv4 "aws:amz:us-west-2:bedrock-agentcore" \ --user "$AWS_ACCESS_KEY_ID:$AWS_SECRET_ACCESS_KEY" \ -H "x-amz-security-token: $AWS_SESSION_TOKEN" \ -H "Content-Type: application/json" \ -H "X-Amzn-Bedrock-AgentCore-Runtime-Session-Id: $(uuidgen)" \ -d "{\"prompt\": \"$PROMPT\"}" \ -X POST \ "$GATEWAY_URL" echo "" sleep 2 done

스크립트를 실행합니다.

bash loadgen.sh

9단계: 결과 가져오기

A/B 테스트를 폴링하여 샘플 크기가 증가함에 따라 결과를 모니터링합니다. 폴링은 통계적 유효성에 영향을 주지 않습니다.

AgentCore CLI

현재 결과 가져오기(6단계의 작업 ID<ab-test-id>로 대체):

agentcore view ab-test <ab-test-id>

결과를 JSON으로 가져오기:

agentcore view ab-test <ab-test-id> --json
AWS SDK (boto3)

결과가 통계적 유의성에 도달할 때까지 폴링:

import boto3 import time client = boto3.client("bedrock-agentcore", region_name="us-west-2") ab_test_id = "customerSupportPromptTest-Ab1Cd2Ef3G" while True: response = client.get_ab_test(abTestId=ab_test_id) status = response["status"] exec_status = response["executionStatus"] print(f"Status: {status}, Execution: {exec_status}") results = response.get("results") if results: print(f"Analysis timestamp: {results.get('analysisTimestamp')}") for metric in results["evaluatorMetrics"]: evaluator = metric["evaluatorArn"] control = metric["controlStats"] print(f"\nEvaluator: {evaluator}") print(f" Control: mean={control['mean']:.3f}, n={control['sampleSize']}") for variant in metric["variantResults"]: print(f" {variant['variantName']}: mean={variant['mean']:.3f}, " f"n={variant['sampleSize']}, " f"pValue={variant.get('pValue', 'N/A')}, " f"significant={variant['isSignificant']}") if variant["isSignificant"]: print(f" >>> Statistically significant! " f"Change: {variant.get('percentChange', 0):.1f}%") # Check if any evaluator has reached significance all_significant = all( variant["isSignificant"] for metric in results["evaluatorMetrics"] for variant in metric["variantResults"] ) if all_significant: print("\nAll evaluators have reached statistical significance.") break time.sleep(300) # Poll every 5 minutes
참고

결과가 표시되는 데 걸리는 시간은 주로 온라인 평가 구성에 구성된 세션 제한 시간에 따라 달라집니다. 제한 시간 내에 새 요청이 도착하지 않으면 세션이 완료된 것으로 간주됩니다. 세션이 종료된 후 결과는 일반적으로 15분 이내에 나타납니다. 더 많은 세션이 완료되면 결과가 누적됩니다. 샘플 크기에 따라 통계적 유의성이 향상됩니다.

결과 해석
  • p-값 < 0.05 및 양percentChange수: 처리가 컨트롤보다 훨씬 더 좋습니다. 처리 배포를 고려합니다.

  • p-값 < 0.05 및 음percentChange수: 처리가 상당히 더 나빠졌습니다. 컨트롤을 유지합니다.

  • p-value >= 0.05: 차이를 결론지을 증거가 충분하지 않습니다. 샘플을 계속 수집하거나 처리 트래픽을 늘립니다.

  • 모든 평가자 확인: 처리는 다른 지표를 회귀하는 동안 한 지표를 개선할 수 있습니다. 결정하기 전에 모든 평가자 결과를 검토합니다.

결과 구조 및 필드 정의에 대한 자세한 설명은 대상 기반 라우팅 가이드의 결과 이해를 참조하세요.

10단계: 결과 확인 및 A/B 테스트 중지

A/B 테스트가 통계적 유의성에 도달하면 결과를 검토하고 실험을 중지합니다.

  1. 중요도를 확인합니다. 대상 평가자가 처리 변형percentChangeisSignificant: true 대해 및 긍정이 있는지 확인합니다(또는 처리가 회귀된 경우 제어가 승자인지 확인).

  2. A/B 테스트를 중지합니다. agentcore stop ab-test -i <ab-test-id>를 실행합니다. 트래픽 라우팅이 즉시 종료되고 모든 요청이 기본 구성으로 돌아갑니다. 보기, 일시 중지, 재개 및 중지를 참조하세요.

11단계: 당첨자 배포

A/B 테스트를 중지한 후 모든 트래픽을 대상 구성 번들 버전으로 라우팅합니다.

agentcore promote ab-test -i <ab-test-id> agentcore deploy

promote는 A/B 테스트(아직 실행 중인 경우)를 중지하고 제어 구성 번들을 업데이트하여 처리 버전을 사용합니다. 를 실행agentcore deploy하여 변경 사항을 적용합니다.

또는 다음 중 하나를 수행하여 당첨자를 수동으로 배포할 수 있습니다.

  • 옵션 A: AgentCore Gateway 라우팅 규칙을 사용하여 모든 트래픽을 대상 구성 번들 버전으로 라우팅합니다.

  • 옵션 B: 대상 시스템 프롬프트를 사용하도록 제어 구성 번들을 업데이트하고 재배포합니다.

  • 옵션 C: 에이전트 코드에서 당첨 번들 버전을 기본값으로 설정하고 A/B 테스트 구성을 제거합니다.

다음 단계

당첨자를 배포한 후:

  • A/B 테스트를 삭제하여 리소스를 정리합니다. A/B 테스트 삭제를 참조하세요.

  • 새 기준을 모니터링합니다. 온라인 평가는 성공 구성에 대한 세션 점수를 계속 매깁니다. 회귀를 감시합니다.

  • 다음 반복을 시작합니다. 우승 구성의 새로운 트레이스는 다음 권장 사항 주기의 토대를 제공합니다. 작동 방식을 참조하세요.

예: A/B 테스트 도구 설명

동일한 구성 번들 패턴을 사용하여 최적화된 도구 설명을 테스트할 수 있습니다. 에이전트가 번들을 직접 읽는 시스템 프롬프트 A/B 테스트와 달리 도구 설명 재정의를 AgentCore Gateway에서 적용합니다. 에이전트가 게이트웨이를 tools/list 통해를 호출하면 게이트웨이는 구성 번들을 읽고 재정의가 적용된 도구 설명을 반환합니다. 에이전트 코드를 변경할 필요가 없습니다.

게이트웨이가 도구 설명 재정의를 적용하는 방법에 대한 자세한 내용은 MCP 대상에 대한 동작을 참조하세요.

구성 번들

컨트롤 번들 - 현재 도구 설명:

agentcore add config-bundle \ --name toolDescControl \ --components '{ "arn:aws:bedrock-agentcore:us-west-2:123456789012:runtime/csAgent-abc123": { "configuration": { "tools": { "lookup_order": { "description": "Look up an order by ID." }, "initiate_return": { "description": "Initiate a return for an order." }, "apply_discount": { "description": "Apply a discount to an order." } } } } }' agentcore deploy

처리 번들 - 권장 사항의 최적화된 도구 설명:

agentcore add config-bundle \ --name toolDescTreatment \ --components '{ "arn:aws:bedrock-agentcore:us-west-2:123456789012:runtime/csAgent-abc123": { "configuration": { "tools": { "lookup_order": { "description": "Look up order details including status, item, and total by order ID. Use when the customer asks about an order or references an order number." }, "initiate_return": { "description": "Start a return process for an order. Use only when the customer explicitly requests a return or exchange, not for order status inquiries." }, "apply_discount": { "description": "Apply a percentage discount to an order. Use when compensating for service issues such as delivery delays. Requires a reason." } } } } }' agentcore deploy

작동 방식

  1. 에이전트가 게이트웨이(MCP 대상)를 tools/list 통해를 호출하면 A/B 테스트는 각 세션을 게이트웨이의 변형(제어 또는 처리)에 할당하고 해당 구성 번들을 확인합니다.

  2. Gateway는 구성 번들을 읽고 재정의가 적용된 도구 설명을 반환합니다.

  3. 에이전트는 도구 선택에 반환된 설명을 사용하므로 에이전트 코드를 변경할 필요가 없습니다.

A/B 테스트 생성

agentcore run ab-test \ --mode config-bundle \ --name toolDescTest \ --gateway csGateway \ --runtime csAgent \ --control-bundle toolDescControl \ --control-version <control-bundle-version-id> \ --treatment-bundle toolDescTreatment \ --treatment-version <treatment-bundle-version-id> \ --online-eval customerSupportEval \ --control-weight 80 \ --treatment-weight 20

나머지 단계(트래픽 전송, 결과 가져오기, 당첨자 배포)는 이전 시스템 프롬프트 예제와 동일합니다.

문제 해결

A/B 테스트 문제(예: 트래픽 전송 후 결과 누락)를 해결하려면 대상 기반 라우팅 가이드의 문제 해결을 참조하세요.