Skip to main content

Production-ready evaluation framework for AI agents — 58 metrics (25 native + 33 Harness Config) across 7 evaluation gates: goal achievement, behavioral integrity, reliability, performance, security, multi-agent coordination, and observability

Project description

Agent Evaluator

PyPI version Python Version License: MIT Version

AI 에이전트 배포 준비도를 7개 Gate로 판정하는 Harness Engineering 평가 SDK

에이전트가 "잘 동작하는가?"를 넘어 "프로덕션에 배포할 준비가 됐는가?" 를 묻습니다. 목표 달성(A) · 행동 무결성(B) · 신뢰성(C) · 성능 계약(D) · 보안 경계(E) · 멀티에이전트 조율(F) · 관측 가능성(G) — 7개 Harness Gate가 에이전트의 배포 준비도를 종합 판정합니다.

데코레이터 한 줄로 LangChain · CrewAI · AutoGen 등 21개 프레임워크를 자동 인식하고, **58개 지표(25 Native Trackers + 33 Harness Config)**를 코드 수정 없이 측정합니다.


Harness Engineering — 7개 Gate로 AI 에이전트 배포 준비도 판정

단순 정확도 측정이 아닌 배포 준비도(deployment readiness) 를 기준으로 에이전트를 평가합니다. 33개 Harness Config를 데코레이터 파라미터로 전달하면, PerformanceMonitor가 자동 집계해 7개 Gate의 PASS/WARN/FAIL을 판정합니다.

from agent_evaluator import (
    InstructionConfig, GoalAlignmentConfig,          # Gate A — 목표 달성
    LoopDetectionConfig, StateConsistencyConfig,      # Gate B — 행동 무결성
    FaultToleranceConfig, GracefulDegradationConfig,  # Gate C — 신뢰성
    SLAConfig, EfficiencyConfig,                      # Gate D — 성능 계약
    ThreatSeverityConfig, ComplianceConfig,           # Gate E — 보안 경계
    ConsensusConfig, AgentRoleConfig,                 # Gate F — 멀티에이전트 조율
    ExplainabilityConfig, ObservabilityConfig,        # Gate G — 관측 가능성
)
from agent_evaluator.decorators import agent_eval

@agent_eval(monitor, task_type="qa",
    instructions=InstructionConfig(required_keywords=["서울"], fail_on_violation=True),
    loop_detection=LoopDetectionConfig(consecutive_repeat_threshold=3),
    sla=SLAConfig(p95_ms=3000),
    explainability=ExplainabilityConfig(min_reasoning_length=20),
)
def my_agent(question: str, ground_truth: str = "") -> str:
    return llm.invoke(question)

monitor.save_to_file("eval")   # eval.json + eval.html — Gate A–G 판정 포함
Gate 영역 판정 기준 Harness Config (개수)
A 🟢 Goal Achievement 지시 이행률 · 목표 정렬 · 계획 일관성 · 컨텍스트 유지 InstructionConfig · GoalAlignmentConfig · PlanConfig · SubtaskConfig · ContextRetentionConfig · KnowledgeRetentionConfig (6)
B 🔵 Behavioral Integrity 루프 탐지 · 범위 일탈 · 도구 안전성 · 상태 일관성 · 교착 탐지 LoopDetectionConfig · ScopeConfig · ToolParameterSafetyConfig · ContextWindowConfig · StateConsistencyConfig · DeadlockConfig (6)
C 🟡 Reliability 재현 가능성 · 오류 복구율 · 품질 하한 · 멱등성 ReproducibilityConfig · FaultToleranceConfig · GracefulDegradationConfig · RetryConsistencyConfig · IdempotencyConfig (5)
D 🔵 Performance Contract SLA 준수율 · 토큰 효율 · TTFT 변동성 · 비용 예측 가능성 SLAConfig · EfficiencyConfig · ResourceBudgetConfig · TTFTVariabilityConfig · CostPredictabilityConfig (5)
E 🔴 Security Boundary 위협 심각도 · 규정 준수 · 위협 대응 행동 ThreatSeverityConfig · ComplianceConfig · ThreatResponseConfig (3)
F 🟣 Multi-Agent Coordination 에이전트 간 합의율 · 정보 전파 정확도 · 역할 준수 · 충돌 해결 ConsensusConfig · PropagationConfig · AgentRoleConfig · ConflictResolutionConfig (4)
G 🩵 Observability 추론 설명 가능성 · 내부 상태 추적 · 오류 진단 · 지연 원인 분석 ExplainabilityConfig · ObservabilityConfig · ErrorDiagnosisConfig · LatencyAttributionConfig (4)

각 Gate는 25개 Native Tracker(Layer 1 기반 지표 6개 + Layer 2 에이전틱 지표 10개 + 보안 지표 5개 + LLMJudge)로부터 원시 측정값을 받아 집계됩니다.

전체 실전 예제: Evaluator_Examples/ch03_harness_basics.py | 대시보드: agent-eval dashboard


왜 데코레이터인가?

# ❌ 기존 방식 — 에이전트 코드를 직접 수정, 보일러플레이트 작성 필요
import time, uuid
from datetime import datetime

def my_agent(question, ground_truth):
    start = time.time()
    response = llm.invoke(question)
    elapsed = time.time() - start

    task = TaskResult(
        task_id=str(uuid.uuid4()), task_type="qa", success=True,
        completion_score=1.0,
        accuracy_score=compute_accuracy(response, ground_truth),  # 직접 계산
        execution_time=elapsed,                                    # 직접 측정
        tokens_used=extract_tokens(response),                      # 프레임워크마다 다름
        tool_calls=[], attempts=1, errors=[], timestamp=datetime.now(),
        question=question, response=str(response), ground_truth=ground_truth,
    )
    monitor.record_task(task)
    return response
# ✅ 데코레이터 방식 — 한 줄 추가, 에이전트 코드 무수정
from agent_evaluator import QuickEval

eval = QuickEval("results/")

@eval.qa                                   # 이 한 줄이 전부
def my_agent(question, ground_truth=""):
    return llm.invoke(question)            # 에이전트 로직 그대로 유지

데코레이터는 **비침습적(non-invasive)**입니다. 원본 함수의 시그니처·반환값·예외 처리가 변경되지 않으며, 측정이 끝나면 원래 반환값이 그대로 호출자에게 전달됩니다.


데코레이터 동작 원리

호출자
  │
  ▼
@agent_eval / @batch_eval / @conversation_eval
  │
  ├─ [1] 실행 시간 측정 시작
  ├─ [2] 원본 함수 실행
  ├─ [3] 프레임워크 어댑터 적용   ← tool_calls · chain_steps · tokens_used 자동 추출
  ├─ [4] EvalMetadata 병합        ← 함수가 (response, EvalMetadata(...)) 반환 시
  ├─ [5] TaskResult 자동 구성     ← 24개 필드 완성
  ├─ [6] PerformanceMonitor.record_task() 호출
  │       ├─ Layer 1: TCR · Accuracy · Hallucination · Quality · Latency · Token
  │       ├─ Layer 2: Tool · Retry · Coordination · Workflow · Security (5종)
  │       ├─ Layer 3: LLMJudge · DeepEval · Ragas  (opt-in)
  │       └─ Harness: 33개 Config 자동 집계 → Gate A–G 통과/경고/실패 판정
  │
  └─ [7] 원본 반환값 그대로 호출자에게 전달

설치

# 기본 설치 — LLMJudge · 대시보드 · OTEL 모니터링 · PDF 포함 (sdk 기본 내장)
pip install agent-evaluator

# ── Evaluator_Examples/ 예제 실행 ─────────────────────────────────────────
pip install "agent-evaluator[examples]"           # 모든 예제 실행 가능 (기본 + eval)

# ── 프레임워크 확장 (사용자 에이전트 코드가 필요로 하는 경우) ──────────────
# agent-evaluator 자체는 아래 패키지 없이도 완전히 동작 (duck typing 방식)
pip install "agent-evaluator[eval]"               # DeepEval ≥3.0 + Ragas ≥0.4 (외부 평가)
pip install "agent-evaluator[langchain]"          # LangChain ≥1.0 / LangGraph ≥1.0
pip install "agent-evaluator[dspy]"               # DSPy ≥2.0
pip install "agent-evaluator[pydanticai]"         # PydanticAI ≥1.0
pip install "agent-evaluator[crewai]"             # CrewAI ≥1.0 (무거움 — 전이 의존성 100개+)
pip install "agent-evaluator[autogen]"            # AutoGen ≥0.3 (무거움)

# ── 조합 편의 ──────────────────────────────────────────────────────────────
pip install "agent-evaluator[full]"               # 전체 (⚠️ crewai/autogen 포함, 10분+ 소요)

3가지 데코레이터

Agent Evaluator의 평가 인터페이스는 호출 패턴에 따라 정확히 3종으로 구성됩니다.

데코레이터 호출 패턴 사용 시나리오
@agent_eval 함수 1회 호출 = TaskResult 1건 단일 QA · 도구 호출 · RAG · 보안 검사
@batch_eval 함수 1회 호출 = TaskResult N건 데이터셋 일괄 평가 · 벤치마크
@conversation_eval 함수 N회 호출 = TaskResult 1건 멀티턴 대화 · 챗봇 세션

데코레이터 1: @agent_eval

1번 호출 → 1개 TaskResult. 동기·비동기·제너레이터·재시도를 모두 지원합니다.

from agent_evaluator import PerformanceMonitor
from agent_evaluator.decorators import agent_eval, RetryConfig, SecurityConfig, LLMJudgeConfig

monitor = PerformanceMonitor("results/")

# 기본 — QA 평가
@agent_eval(monitor, task_type="qa")
def agent(question: str, ground_truth: str = "") -> str:
    return llm.invoke(question)

# 비동기 함수 — 동일한 데코레이터 사용
@agent_eval(monitor, task_type="qa")
async def async_agent(question: str, ground_truth: str = "") -> str:
    return await async_llm.invoke(question)

# 재시도 내장 — RetryConfig 로 재시도 정책 구성, attempts 필드 자동 기록
@agent_eval(monitor, task_type="qa", retry=RetryConfig(max=3, delay=1.0, backoff=2.0))
def robust_agent(question: str, ground_truth: str = "") -> str:
    return unreliable_llm.invoke(question)

# RAG 에이전트 — rag_mode=True 하나로 context + hallucination 자동 활성
@agent_eval(monitor, task_type="information_retrieval", rag_mode=True, context_arg="context")
def rag_agent(question: str, context: str = "", ground_truth: str = "") -> str:
    return retrieval_llm.invoke(question, context)

# 보안 검사 — security=SecurityConfig() 로 5개 보안 트래커 임시 활성
@agent_eval(monitor, task_type="qa", security=SecurityConfig())
def secure_agent(question: str, ground_truth: str = "") -> str:
    return llm.invoke(question)

# LLM 프레임워크 어댑터 — tool_calls · tokens_used 자동 추출
@agent_eval(monitor, task_type="tool_use", framework="langchain")
def langchain_agent(question: str, ground_truth: str = "") -> str:
    return executor.invoke({"input": question})

@agent_eval 주요 파라미터

파라미터 기본값 설명
task_type "qa" 태스크 유형 (qa · tool_use · information_retrieval · code_generation 등)
framework "native" 프레임워크 어댑터 (21종 지원)
question_arg "question" 질문 인자명
ground_truth_arg "ground_truth" 정답 인자명
context_arg None RAG 컨텍스트 인자명
expected_tools_arg None 기대 툴 목록 인자명 (Tool Selection F1 자동 계산)
score_fn None 커스텀 정확도 계산 함수 (response, gt) → float
rag_mode False context_arg + hallucination 자동 활성 단축 설정
retry None RetryConfig 인스턴스 — 재시도 정책 (max · delay · backoff · jitter_type 등)
security None SecurityConfig 인스턴스 — 보안 지표 이 호출에만 임시 활성
llm_judge None LLMJudgeConfig 인스턴스 — LLM Judge 이 호출에만 임시 활성
enable_hallucination_detection False Hallucination Detection 이 호출에만 임시 활성
enable_anomaly_detection False AnomalyDetector 이 호출에만 임시 활성
timeout None 최대 실행 시간(초)
sample_rate 1.0 기록 샘플링 비율
on_record None 기록 직전 콜백 (TaskResult 교체 가능)
alert_rules [] 조건부 알림 규칙 목록
flush_every 0 N건마다 자동 save_to_file()
preset None 사전 정의 설정 묶음

데코레이터 2: @batch_eval

1번 호출 → N개 TaskResult. 질문 리스트를 받아 건별로 독립된 평가 레코드를 생성합니다.

from agent_evaluator.decorators import batch_eval

# 기본 — 리스트 입력, 리스트 반환
@batch_eval(monitor, task_type="qa")
def batch_agent(questions: list, ground_truths: list = None) -> list:
    return [llm.invoke(q) for q in questions]

# DataFrame 반환 — accuracy_score · execution_time · tokens_total 등 포함
@batch_eval(monitor, task_type="qa", return_format="dataframe")
def batch_agent_df(questions: list, ground_truths: list = None) -> list:
    return [llm.invoke(q) for q in questions]

# 병렬 실행 (async 함수) — asyncio.gather 기반
@batch_eval(monitor, task_type="qa", concurrent=True, max_concurrent=4)
async def parallel_agent(questions: list, ground_truths: list = None) -> list:
    return await asyncio.gather(*[async_llm.invoke(q) for q in questions])

# 진행률 콜백 — 대규모 배치 모니터링
@batch_eval(
    monitor,
    task_type="qa",
    return_format="tuple",                              # (responses, task_results) 반환
    on_batch_progress=lambda done, total: print(f"{done}/{total}"),
    flush_every=100,                                    # 100건마다 중간 저장
)
def large_batch(questions: list, ground_truths: list = None) -> list:
    return [llm.invoke(q) for q in questions]

responses, task_results = large_batch(questions, ground_truths)

@batch_eval 주요 파라미터

파라미터 기본값 설명
questions_arg "questions" 질문 리스트 인자명
ground_truths_arg "ground_truths" 정답 리스트 인자명
return_format "list" 반환 형식: "list" · "tuple" · "dataframe"
concurrent False async 함수 항목별 병렬 실행
max_concurrent 0 병렬 상한 (0 = 무제한)
shuffle False 처리 순서 무작위화
item_timeout None 항목별 최대 처리 시간(초)
on_batch_progress None 진행률 콜백 (completed, total) → None
on_batch_complete None 배치 완료 콜백 (results) → None
on_item_error None 항목 실패 콜백 (index, question, error) → None
streaming_mode False 메모리 효율적 스트리밍 처리

데코레이터 3: @conversation_eval

N번 호출 → 1개 TaskResult. 동일 session_id로 반복 호출하면 내부에서 턴을 누적하다가 max_turns 도달 또는 flush_conversation() 호출 시 세션을 종료하고 지표를 계산합니다.

from agent_evaluator.decorators import conversation_eval

# 기본 — session_id별 자동 누적, max_turns 도달 시 자동 flush
@conversation_eval(monitor, session_id_arg="session_id", max_turns=5)
def chat(question: str, session_id: str = "default") -> str:
    return llm.invoke(question)

# 사용 — 동일 session_id로 반복 호출
chat("파이썬 비동기 처리 방법 알려줘", session_id="conv_001")
chat("방금 설명한 방법의 단점은?",      session_id="conv_001")
chat("asyncio.gather 예시 코드 보여줘", session_id="conv_001")
# → 5턴 도달 시 자동 flush: context_retention · topic_coherence · progressive_depth 계산

# 수동 flush — 원하는 시점에 세션 종료
from agent_evaluator.decorators import flush_conversation
flush_conversation("conv_001")

# 턴별 콜백 + 세션 스코어 함수
@conversation_eval(
    monitor,
    max_turns=10,
    on_turn=lambda sid, user, resp, meta: print(f"[{sid}] {user[:20]}…"),
    session_score_fn=lambda metrics: metrics.overall_score * 100,
    flush_every=3,                    # 세션 3개마다 save_to_file() 자동 호출
)
def advanced_chat(question: str, session_id: str = "s1") -> str:
    return llm.invoke(question)

@conversation_eval이 측정하는 지표:

지표 설명
turn_count 누적 대화 턴 수
overall_score 세션 종합 점수 (0–1)
context_retention 이전 턴 맥락이 후속 응답에 반영된 정도
topic_coherence 대화 전반의 주제 일관성
progressive_depth 대화가 심화될수록 정보 밀도가 높아지는 정도
session_completion 목표 대화 완성도
avg_turn_latency 턴별 평균 응답 시간
turn_scores 턴별 품질 점수 (Optional)

@conversation_eval 주요 파라미터

파라미터 기본값 설명
session_id_arg "session_id" 세션 ID 인자명
user_arg "question" 사용자 메시지 인자명
max_turns None 최대 턴 수 (도달 시 자동 flush)
max_turns_exceeded_action "flush" 초과 시 동작: "flush" · "warn" · "error"
flush_on_error True 예외 발생 시 세션 자동 flush
on_turn None 턴 완료 콜백 (sid, user, response, meta) → None
on_flush None 세션 종료 콜백 (metrics, session_id) → None
session_score_fn None 세션 종합 점수 함수 (ConversationMetrics) → float
turn_score_fn None 턴별 점수 함수 (user, response, meta) → float
load_previous_session False 이전 세션 이어받기
max_session_seconds None 비활성 세션 자동 flush 타이머(초)

EvalDecorator — 3종 통합 팩토리

공통 설정(monitor, framework, model_name 등)을 한 번만 정의하고 3종 데코레이터 모두에 재사용합니다.

from agent_evaluator.decorators import EvalDecorator

# 공통 설정 한 번 정의
dec = EvalDecorator(
    monitor,
    framework="langchain",
    model_name="gpt-4o-mini",
    flush_every=10,
    alert_rules=[slow_rule, error_rule],
)

# ── agent_eval 계열 ──────────────────────────────────
@dec(task_type="qa")                                   # agent_eval 직접 호출
def qa_agent(question, ground_truth=""): ...

@dec.with_retry(task_type="qa", retry=RetryConfig(max=3))  # 재시도 포함
def robust_agent(question, ground_truth=""): ...

# ── batch_eval ───────────────────────────────────────
@dec.batch(task_type="qa", return_format="dataframe")
def batch_agent(questions, ground_truths=None): ...

# ── conversation_eval ────────────────────────────────
@dec.conversation(session_id_arg="sid", max_turns=5)
def chat(question, sid="s1"): ...

# ── task_type 단축 속성 (QuickEval과 동일한 API) ─────
@dec.qa             # task_type="qa"
@dec.tool_use       # task_type="tool_use"
@dec.rag            # task_type="information_retrieval" + rag_mode=True
@dec.code           # task_type="code_generation"
@dec.reasoning      # task_type="reasoning"
@dec.secure         # task_type="qa" + security=SecurityConfig()

QuickEval — 1줄 시작 Facade

PerformanceMonitor + EvalDecorator를 1줄로 구성하는 원스톱 진입점입니다.

from agent_evaluator import QuickEval

# 기본 초기화
eval = QuickEval("results/")

# 용도별 팩토리 — 관련 옵션 자동 설정
eval = QuickEval.for_rag("results/")               # hallucination_detection=True 기본 활성
eval = QuickEval.for_security("results/")          # enable_security_metrics=True 기본 활성
eval = QuickEval.for_llm_judge("results/", model="claude-sonnet-4-6")

# 데코레이터 단축 속성 11종
@eval.qa            @eval.tool_use      @eval.rag
@eval.code          @eval.reasoning     @eval.planning
@eval.data_analysis @eval.creative      @eval.multi_agent
@eval.secure        @eval.streaming

# 배치 · 대화 데코레이터도 동일 인터페이스
@eval.batch(task_type="qa", return_format="dataframe")
def batch_agent(questions, ground_truths=None): ...

@eval.conversation(session_id_arg="sid", max_turns=5)
def chat(question, sid="s1"): ...

# 결과 저장 · 게이팅
eval.save()                                        # results/*.json + *.html
eval.gate(tcr=85, accuracy=70, hallucination=5)    # CI/CD 게이트
eval.summary()                                     # 주요 지표 요약 출력
eval.export_to_dataframe()                         # pd.DataFrame 반환

eval_context — 데코레이터 불가 시 탈출구

외부 라이브러리 함수, lambda, 동적 호출 등 데코레이터를 붙일 수 없는 코드에서 사용합니다. @agent_eval과 동일한 평가를 수행합니다.

from agent_evaluator.decorators import eval_context, get_eval_ctx

# 기본 — with 블록 종료 시 자동 record_task()
with eval_context(monitor, task_type="qa",
                  question="한국의 수도는?", ground_truth="서울") as ctx:
    ctx.response = external_lib.call("한국의 수도는?")

# get_eval_ctx() 로 추가 메타데이터 주입
with eval_context(monitor, task_type="tool_use", question=q) as ctx:
    result = external_agent.run(q)
    ctx.response = result["output"]
    ec = get_eval_ctx()
    if ec:
        ec.framework = "langchain"
        ec.chain_steps = parse_steps(result)

# 비동기
async with eval_context(monitor, task_type="qa", question=q) as ctx:
    ctx.response = await async_external.call(q)

EvalMetadata — 추가 메타데이터 주입

3종 데코레이터 모두에서 사용 가능합니다. 반환값을 (response, EvalMetadata(...)) 튜플로 바꾸면 자동 추출 결과를 덮어쓸 수 있습니다.

from agent_evaluator.decorators import EvalMetadata

@agent_eval(monitor, task_type="tool_use")
def agent(question, ground_truth=""):
    response = llm.invoke(question)
    return response, EvalMetadata(
        accuracy_score=0.95,                        # 커스텀 점수 직접 지정
        tool_calls=["search", "calculator"],        # 툴 호출 목록
        tokens_used={"input": 120, "output": 80},
        chain_steps=["search", "parse", "answer"],
        agent_interactions=[("planner", "executor", "task_complete")],
    )

@conversation_eval에서는 TurnMetadata를 사용합니다.

from agent_evaluator.decorators import TurnMetadata

@conversation_eval(monitor, max_turns=5)
def chat(question: str, session_id: str = "s1") -> str:
    response = llm.invoke(question)
    return response, TurnMetadata(
        model="gpt-4o-mini",
        tokens={"input": 50, "output": 30},
        tool_calls=["search"],
    )

21개 프레임워크 자동 인식

framework= 파라미터 하나로 응답 객체에서 tool_calls, chain_steps, tokens_used 등을 자동 추출합니다. 3종 데코레이터 모두 동일한 framework= 파라미터를 지원합니다.

# 명시적 지정 — IDE 자동완성 지원 (FrameworkLiteral 타입 힌트)
@agent_eval(monitor, task_type="tool_use", framework="langchain")
def lc_agent(question, ground_truth=""): ...

# 자동 감지 (기본 활성 — auto_detect_framework=True)
@agent_eval(monitor, task_type="qa")
def auto_agent(question, ground_truth=""): ...

# batch_eval · conversation_eval에도 동일하게 적용
@batch_eval(monitor, task_type="qa", framework="openai")
def batch_agent(questions, ground_truths=None): ...

@conversation_eval(monitor, max_turns=5, framework="anthropic")
def chat(question, session_id="s1"): ...

# 프레임워크 어댑터 정보 조회
from agent_evaluator.decorators import get_framework_info
info = get_framework_info("langchain")
# → {"name": "LangChain", "extras": "langchain",
#    "extracts": ["tool_calls", "chain_steps"], "async_supported": True, ...}

어댑터 전체 목록

참고: framework= 파라미터와 어댑터는 duck typing 방식으로 동작 — agent-evaluator 자체는 해당 프레임워크 패키지 없이도 완전히 동작한다. "필요 extras" 열은 사용자의 에이전트 코드가 해당 프레임워크를 import할 때 필요한 패키지다.

식별자 이름 필요 extras 자동 추출 필드 async
langchain LangChain [langchain]¹ tool_calls · chain_steps
langgraph LangGraph [langchain]¹ state_transitions · graph_traversal · tool_calls · chain_steps
crewai CrewAI [crewai]¹ agent_interactions
autogen AutoGen [autogen]¹ conversation_turns · tokens_used
dspy DSPy [dspy] chain_steps · tokens_used
pydanticai PydanticAI [pydanticai] chain_steps · tokens_used
anthropic Anthropic [llm] tool_calls · tokens_used
openai OpenAI [llm] tool_calls · tokens_used
gemini Google Gemini [llm] tool_calls · tokens_used
vertexai Vertex AI [llm] tool_calls · tokens_used
cohere Cohere [llm] tool_calls · tokens_used
groq Groq [llm] tool_calls · tokens_used
mistral Mistral AI [llm] tool_calls · tokens_used
bedrock AWS Bedrock [llm] tool_calls · tokens_used
ollama Ollama [llm] tool_calls · tokens_used
llamaindex LlamaIndex [llm] chain_steps
haystack Haystack [llm] chain_steps
semantic_kernel Semantic Kernel [llm] chain_steps · tokens_used
smolagents HuggingFace smolagents [llm] tool_calls · chain_steps
vllm vLLM [llm] tool_calls · tokens_used
huggingface HuggingFace [llm] chain_steps · tool_calls

¹ 사용자 프레임워크 extras — agent-evaluator 자체는 이 패키지 없이 동작. @agent_eval(framework="langchain") 데코레이터는 duck typing으로 작동하므로 agent-evaluator 설치 시에는 불필요. 사용자의 에이전트 코드가 해당 프레임워크를 직접 import할 때만 설치.


오케스트레이션 프레임워크

LangChain

AgentExecutor.invoke() 결과의 intermediate_steps에서 툴 호출과 체인 단계를 자동 추출합니다.

from langchain.agents import AgentExecutor
from agent_evaluator.decorators import agent_eval

# intermediate_steps → tool_calls + chain_steps 자동 변환
# usage_metadata / response_metadata.token_usage → tokens_used 자동 추출
@agent_eval(monitor, task_type="tool_use", framework="langchain")
def lc_agent(question: str, ground_truth: str = "") -> str:
    result = agent_executor.invoke({"input": question})
    return result  # dict 그대로 반환 — "output" 키에서 텍스트 자동 추출

# 프레임워크 전용 별칭 (agent_evaluator.integrations)
from agent_evaluator.integrations import langchain_eval

@langchain_eval(monitor, task_type="tool_use")
def lc_agent2(question: str, ground_truth: str = "") -> str:
    return agent_executor.invoke({"input": question})

LangGraph

그래프 실행 결과의 messages 배열에서 상태 전이·그래프 경로·툴 호출을 추출합니다. __metadata__ 키가 있으면 그래프 메타데이터도 자동 수집합니다.

from langgraph.graph import StateGraph
from agent_evaluator.decorators import agent_eval

# messages → state_transitions + graph_traversal
# ToolMessage / AIMessage → chain_steps + 타임스탬프 기반 실행 시간
@agent_eval(monitor, task_type="tool_use", framework="langgraph")
def lg_agent(question: str, ground_truth: str = "") -> str:
    result = graph.invoke({"messages": [("user", question)]})
    return result  # "messages"[-1].content 자동 추출

from agent_evaluator.integrations import langgraph_eval

@langgraph_eval(monitor, task_type="tool_use")
def lg_agent2(question: str, ground_truth: str = "") -> str:
    return graph.invoke({"messages": [("user", question)]})

CrewAI

Crew.kickoff() 결과의 tasks_output에서 에이전트 간 상호작용을 추출합니다. output_pydantic / output_format (v2.x) 필드를 지원합니다.

from crewai import Crew, Agent, Task
from agent_evaluator.decorators import agent_eval

# tasks_output → agent_interactions 자동 변환
# 주의: CrewAI는 async 미지원 — 동기 함수로만 사용
@agent_eval(monitor, task_type="tool_use", framework="crewai")
def crew_agent(question: str, ground_truth: str = "") -> str:
    result = crew.kickoff(inputs={"topic": question})
    return str(result)

from agent_evaluator.integrations import crewai_eval

@crewai_eval(monitor, task_type="tool_use")
def crew_agent2(question: str, ground_truth: str = "") -> str:
    return str(crew.kickoff(inputs={"topic": question}))

AutoGen

chat_result.messages / chat_history에서 대화 턴과 비용 정보를 추출합니다. AutoGen 0.4+ async API는 autogen_eval_async 전용 데코레이터를 사용합니다.

from autogen import ConversableAgent
from agent_evaluator.decorators import agent_eval
from agent_evaluator.integrations import autogen_eval, autogen_eval_async

# messages/chat_history → conversation_turns
# cost/usage_summary → tokens_used
@agent_eval(monitor, task_type="qa", framework="autogen")
def autogen_agent(question: str, ground_truth: str = "") -> str:
    result = assistant.initiate_chat(user_proxy, message=question, max_turns=3)
    return result.summary

# AutoGen 0.4+ async API 전용
@autogen_eval_async(monitor, task_type="qa")
async def autogen_agent_async(question: str, ground_truth: str = "") -> str:
    result = await team.run(task=question)
    return result.messages[-1].content

LLM 공급자

OpenAI

ChatCompletion 응답의 choices[0].message.tool_callsusage.total_tokens를 자동 추출합니다. Assistants API의 required_action도 지원합니다.

import openai
from agent_evaluator.decorators import agent_eval

client = openai.OpenAI()

@agent_eval(monitor, task_type="tool_use", framework="openai")
def gpt_agent(question: str, ground_truth: str = "") -> str:
    return client.chat.completions.create(
        model="gpt-4o-mini",
        messages=[{"role": "user", "content": question}],
        tools=[...],
    )  # ChatCompletion 객체 그대로 반환 — choices[0].message.content 자동 추출

Anthropic

Message 응답의 content[].tool_useusage.input_tokens/output_tokens를 추출합니다. 캐시 토큰(cache_creation_input_tokens, cache_read_input_tokens, SDK ≥0.29)도 지원합니다.

import anthropic
from agent_evaluator.decorators import agent_eval

client = anthropic.Anthropic()

@agent_eval(monitor, task_type="tool_use", framework="anthropic")
def claude_agent(question: str, ground_truth: str = "") -> str:
    return client.messages.create(
        model="claude-sonnet-4-6",
        max_tokens=1024,
        messages=[{"role": "user", "content": question}],
        tools=[...],
    )  # Message 객체 그대로 반환 — content[0].text 자동 추출

Google Gemini / Vertex AI

GenerateContentResponsecandidates[0].content.parts[].function_callusage_metadata를 추출합니다.

import google.generativeai as genai
from agent_evaluator.decorators import agent_eval

model = genai.GenerativeModel("gemini-1.5-flash")

@agent_eval(monitor, task_type="tool_use", framework="gemini")
def gemini_agent(question: str, ground_truth: str = "") -> str:
    return model.generate_content(question)  # GenerateContentResponse 그대로 반환

# Vertex AI는 동일한 응답 구조 — framework="vertexai"
@agent_eval(monitor, task_type="tool_use", framework="vertexai")
def vertex_agent(question: str, ground_truth: str = "") -> str:
    return vertex_model.generate_content(question)

Cohere

NonStreamedChatResponsetool_callsmeta.tokens를 추출합니다. 스트리밍 응답(finish_reason 속성)도 자동 감지합니다.

import cohere
from agent_evaluator.decorators import agent_eval

co = cohere.Client()

@agent_eval(monitor, task_type="tool_use", framework="cohere")
def cohere_agent(question: str, ground_truth: str = "") -> str:
    return co.chat(message=question, tools=[...])

Groq

OpenAI 호환 API 구조 — tool_callsusage를 추출합니다. 캐시 토큰(cache_creation_input_tokens, cache_read_input_tokens, v0.9+)도 지원합니다.

from groq import Groq
from agent_evaluator.decorators import agent_eval

client = Groq()

@agent_eval(monitor, task_type="tool_use", framework="groq")
def groq_agent(question: str, ground_truth: str = "") -> str:
    return client.chat.completions.create(
        model="llama-3.3-70b-versatile",
        messages=[{"role": "user", "content": question}],
    )

Mistral AI

ChatCompletionResponsetool_callsusage를 추출합니다. 구버전 function_call 필드도 지원합니다.

from mistralai import Mistral
from agent_evaluator.decorators import agent_eval

client = Mistral()

@agent_eval(monitor, task_type="tool_use", framework="mistral")
def mistral_agent(question: str, ground_truth: str = "") -> str:
    return client.chat.complete(
        model="mistral-large-latest",
        messages=[{"role": "user", "content": question}],
    )

AWS Bedrock

Bedrock Converse API 응답에서 model_id 기반으로 Titan / Mistral on Bedrock / Claude 응답을 분기 처리합니다.

import boto3
from agent_evaluator.decorators import agent_eval

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

@agent_eval(monitor, task_type="tool_use", framework="bedrock")
def bedrock_agent(question: str, ground_truth: str = "") -> str:
    return client.converse(
        modelId="anthropic.claude-3-5-sonnet-20241022-v2:0",
        messages=[{"role": "user", "content": [{"text": question}]}],
    )

Ollama

ollama.chat() / ollama.generate() 응답의 tool_callsprompt_eval_count / eval_count를 추출합니다. 주의: Ollama는 async 미지원입니다.

import ollama
from agent_evaluator.decorators import agent_eval

@agent_eval(monitor, task_type="qa", framework="ollama")
def ollama_agent(question: str, ground_truth: str = "") -> str:
    return ollama.chat(
        model="llama3.2",
        messages=[{"role": "user", "content": question}],
    )

AI 프레임워크

DSPy

dspy.Prediction_completions 속성에서 체인 단계를 추출합니다. LM history 전체 multi-step도 지원합니다. 주의: DSPy는 async 미지원입니다.

import dspy
from agent_evaluator.decorators import agent_eval
from agent_evaluator.integrations import dspy_eval

lm = dspy.LM("openai/gpt-4o-mini")
dspy.configure(lm=lm)

@agent_eval(monitor, task_type="qa", framework="dspy")
def dspy_agent(question: str, ground_truth: str = "") -> str:
    predictor = dspy.Predict("question -> answer")
    return predictor(question=question)  # Prediction 객체 → .answer 자동 추출

@dspy_eval(monitor, task_type="qa")
def dspy_agent2(question: str, ground_truth: str = "") -> str:
    return dspy.ChainOfThought("question -> answer")(question=question)

PydanticAI

RunResult.all_messages() (우선) 또는 .messages (fallback)에서 체인 단계를 추출합니다. ToolCallPart / ToolReturnPart / TextPart를 세분화해 추출합니다.

from pydantic_ai import Agent
from agent_evaluator.decorators import agent_eval
from agent_evaluator.integrations import pydanticai_eval

agent = Agent("openai:gpt-4o-mini", system_prompt="...")

@agent_eval(monitor, task_type="qa", framework="pydanticai")
async def pydantic_agent(question: str, ground_truth: str = "") -> str:
    result = await agent.run(question)
    return result  # RunResult 객체 → .data 자동 추출

@pydanticai_eval(monitor, task_type="qa")
async def pydantic_agent2(question: str, ground_truth: str = "") -> str:
    return await agent.run(question)

LlamaIndex

Response.source_nodes에서 체인 단계를 추출합니다. AgentChatResponse.sourcesToolOutput도 지원합니다.

from llama_index.core import VectorStoreIndex
from agent_evaluator.decorators import agent_eval

index = VectorStoreIndex.from_documents([...])
query_engine = index.as_query_engine()

# source_nodes → chain_steps (score + metadata 포함)
@agent_eval(monitor, task_type="information_retrieval", framework="llamaindex", rag_mode=True)
def llamaindex_agent(question: str, ground_truth: str = "") -> str:
    return query_engine.query(question)

Haystack

파이프라인 컴포넌트 출력 dict에서 retriever / generator / reader / embedder / ranker를 chain_steps로 추출합니다.

from haystack import Pipeline
from agent_evaluator.decorators import agent_eval

pipeline = Pipeline()
# ... 컴포넌트 추가 ...

# 컴포넌트 출력 dict → chain_steps
@agent_eval(monitor, task_type="information_retrieval", framework="haystack", rag_mode=True)
def haystack_agent(question: str, ground_truth: str = "") -> str:
    return pipeline.run({"query": question})

Semantic Kernel

inner_content에서 OpenAI / Anthropic 백엔드 토큰을 자동 추출합니다. function_name + plugin_name"Plugin.function" 형식 툴 호출도 지원합니다.

import semantic_kernel as sk
from agent_evaluator.decorators import agent_eval

kernel = sk.Kernel()

# inner_content → tokens_used (OpenAI/Anthropic 백엔드 자동 감지)
@agent_eval(monitor, task_type="tool_use", framework="semantic_kernel")
async def sk_agent(question: str, ground_truth: str = "") -> str:
    result = await kernel.invoke(plugin_name, function_name, input=question)
    return str(result)

HuggingFace smolagents

ToolCall 스텝 목록에서 성공/실패 여부와 입력값을 정규화해 tool_calls + chain_steps로 추출합니다. 주의: smolagents는 async 미지원입니다.

from smolagents import CodeAgent, HfApiModel
from agent_evaluator.decorators import agent_eval

model = HfApiModel()
agent = CodeAgent(tools=[...], model=model)

@agent_eval(monitor, task_type="tool_use", framework="smolagents")
def smol_agent(question: str, ground_truth: str = "") -> str:
    return agent.run(question)

vLLM

OpenAI 호환 API — choices[0].message.tool_callsusage.total_tokens를 추출합니다.

from openai import OpenAI  # vLLM은 OpenAI 호환 클라이언트 사용
from agent_evaluator.decorators import agent_eval

client = OpenAI(base_url="http://localhost:8000/v1", api_key="vllm")

@agent_eval(monitor, task_type="qa", framework="vllm")
def vllm_agent(question: str, ground_truth: str = "") -> str:
    return client.chat.completions.create(
        model="meta-llama/Llama-3.2-3B-Instruct",
        messages=[{"role": "user", "content": question}],
    )

HuggingFace

pipeline() 결과의 generated_text에서 체인 단계를, actions / tool_calls 필드에서 툴 호출을 추출합니다. 주의: HuggingFace는 async 미지원입니다.

from transformers import pipeline
from agent_evaluator.decorators import agent_eval

pipe = pipeline("text-generation", model="Qwen/Qwen2.5-1.5B-Instruct")

@agent_eval(monitor, task_type="qa", framework="huggingface")
def hf_agent(question: str, ground_truth: str = "") -> str:
    return pipe(question, max_new_tokens=200)

자동 감지 (auto_detect_framework=True)

auto_detect_framework=True(기본값)이면 반환 객체의 속성을 검사해 프레임워크를 자동 판별합니다.

감지 조건 판별 프레임워크
stop_reason 속성 존재 (choices 없음) anthropic
choices + usage 속성 존재 openai
candidates + usage_metadata 속성 존재 gemini
meta.tokens 속성 존재 (choices 없음) cohere
x_groq 속성 존재 groq
choices[0].finish_reason == "stop" + mistral 힌트 mistral
ResponseMetadata + bedrock 힌트 bedrock
step_results 속성 존재 smolagents
completions 속성 + DSPy 타입명 dspy
all_messages callable 존재 pydanticai
# framework= 생략 → 자동 감지 (기본값)
@agent_eval(monitor, task_type="qa")
def auto_agent(question: str, ground_truth: str = "") -> str:
    return client.chat.completions.create(...)  # OpenAI → 자동 "openai" 판별

# 자동 감지 명시적 비활성화 (framework= 고정 우선)
@agent_eval(monitor, task_type="qa", framework="openai", auto_detect_framework=False)
def fixed_agent(question: str, ground_truth: str = "") -> str:
    return client.chat.completions.create(...)

58개 지표와 데코레이터 활성화 조건

Layer 1 — 기초 지표 (기본 데코레이터로 자동 활성)

지표 클래스 데코레이터 자동화 주요 출력
Task Completion Rate TaskCompletionTracker 항상 활성 tcr · full_success · partial_success · failures
Accuracy AccuracyEvaluator 항상 활성 (score_fn 없으면 기본 알고리즘) overall_accuracy · median_accuracy · std_accuracy
Response Quality ResponseQualityEvaluator response + request 있으면 자동 dimension_scores · total_score (0–5) · grade
Latency LatencyTracker 함수 실행 시간 자동 측정 mean · p50 · p90 · p95 · p99 · std
Token Economy TokenEconomyTracker 프레임워크 어댑터 자동 추출 total_tokens · total_cost · estimated_monthly_cost
Hallucination HallucinationDetector rag_mode=True 또는 enable_hallucination_detection=True hallucination_rate · unsupported_claims_count · by_severity

Accuracy 계산 방식: Token Overlap(40%) + Jaccard Similarity(30%) + LCS(20%) + 문자 유사도(10%)

Layer 2-A — 에이전틱 지표 (tool_calls · chain_steps 자동 추출 시 활성)

지표 클래스 활성화 조건 주요 출력
Tool Call Analysis ToolCallAnalyzer tool_calls 자동 추출 또는 EvalMetadata efficiency_score · redundancy_rate · failure_rate
Retry & Correction RetryCorrectionTracker retry=RetryConfig(max=N) 파라미터 또는 attempts 필드 retry_rate · first_attempt_success_rate · correction_success_rate
Tool Selection F1 ToolSelectionTracker expected_tools_arg 파라미터 지정 precision · recall · f1_score
Agent Coordination AgentCoordinationTracker agent_interactions 자동 추출 score · pattern_type · unique_agents
Workflow Execution WorkflowExecutionTracker chain_steps · state_transitions 자동 추출 step_success_rate · task_success_rate · bottlenecks

Layer 2-B — 보안 지표 (security=SecurityConfig() 또는 Monitor 전역 설정)

지표 클래스 탐지 대상 주요 출력
Input Sanitization InputSanitizationTracker SQL Injection · Command Injection · XSS · Prompt Injection (40개 패턴) risk_level · threat_count · threat_rate
Output Leakage OutputLeakageDetector API 키 · 비밀번호 · 신용카드 · 개인정보 severity · leakage_count · leakage_rate
Tool Authorization ToolAuthorizationTracker 비인가 툴 사용 · 위험 파라미터 compliance_rate · violation_rate · unauthorized_calls
Privilege Escalation PrivilegeEscalationDetector guest→admin 권한 상승 체인 risk_score (0–10) · escalation_detected · escalation_path
Tool Chain Attack ToolChainAttackDetector 데이터 유출 · 횡적 이동 · 지속성 공격 체인 confidence (0–1) · attack_types · is_suspicious_chain

보안 지표 활성화 방법:

from agent_evaluator.decorators import SecurityConfig

# 방법 A: 특정 함수에만 임시 활성 (이 호출만)
@agent_eval(monitor, task_type="qa", security=SecurityConfig())
def secure_agent(question, ground_truth=""): ...

# 방법 B: Monitor 전역 설정 (모든 record_task에 적용)
monitor = PerformanceMonitor("results/", enable_security_metrics=True)

Layer 3 — 하이브리드 평가 (외부 라이브러리)

from agent_evaluator import HybridPerformanceMonitor

monitor = HybridPerformanceMonitor(
    use_deepeval=True,    # pip install "agent-evaluator[eval]"
    use_ragas=True,
    output_dir="results/",
)

# HybridPerformanceMonitor는 PerformanceMonitor 상속 — 3종 데코레이터 모두 동일하게 사용
@agent_eval(monitor, task_type="information_retrieval", rag_mode=True, context_arg="context")
def rag_agent(question, context="", ground_truth=""): ...
제공자 지표 조건
LLMJudge (v0.7.5+) completeness · relevance · factual · toxicity · bias 기본 설치에 포함 · llm_judge=LLMJudgeConfig()
LLMJudge (v0.7.6+) + faithfulness (RAG) · 커스텀 기준(G-Eval) rag_mode=True + llm_judge=LLMJudgeConfig(criteria=[...])
DeepEval Hallucination(NLI) · Answer Relevancy (LLM) pip install "agent-evaluator[eval]"
Ragas Faithfulness · Answer Relevancy · Context Precision · Context Recall (LLM) 동일 + context 필드 필요

Harness Engineering — 33개 Config, 7개 Gate Group (A–G)

Harness Config는 @agent_eval 데코레이터 파라미터로 전달하며, PerformanceMonitor가 자동 집계합니다. 대시보드 Harness Gate 탭에서 그룹별 통과/경고/실패를 시각화합니다.

from agent_evaluator import (
    InstructionConfig, GoalAlignmentConfig, PlanConfig,   # Group A
    LoopDetectionConfig, StateConsistencyConfig,           # Group B
    FaultToleranceConfig, GracefulDegradationConfig,       # Group C
    SLAConfig, EfficiencyConfig,                           # Group D
    ThreatSeverityConfig, ComplianceConfig,                # Group E
    ConsensusConfig, AgentRoleConfig,                      # Group F
    ExplainabilityConfig, ObservabilityConfig,             # Group G
)

@agent_eval(monitor, task_type="qa",
    instructions=InstructionConfig(required_keywords=["서울"], fail_on_violation=True),
    loop_detection=LoopDetectionConfig(consecutive_repeat_threshold=3),
    sla=SLAConfig(p95_ms=3000),
    explainability=ExplainabilityConfig(min_reasoning_length=20),
)
def my_agent(question: str, ground_truth: str = "") -> str: ...
Group 영역 Config (개수)
A Goal Achievement InstructionConfig · GoalAlignmentConfig · PlanConfig · SubtaskConfig · ContextRetentionConfig · KnowledgeRetentionConfig (6)
B Behavioral Integrity LoopDetectionConfig · ScopeConfig · ToolParameterSafetyConfig · ContextWindowConfig · StateConsistencyConfig · DeadlockConfig (6)
C Reliability ReproducibilityConfig · FaultToleranceConfig · GracefulDegradationConfig · RetryConsistencyConfig · IdempotencyConfig (5)
D Performance Contract SLAConfig · EfficiencyConfig · ResourceBudgetConfig · TTFTVariabilityConfig · CostPredictabilityConfig (5)
E Security Boundary ThreatSeverityConfig · ComplianceConfig · ThreatResponseConfig (3)
F Multi-Agent Coord. ConsensusConfig · PropagationConfig · AgentRoleConfig · ConflictResolutionConfig (4)
G Observability ExplainabilityConfig · ObservabilityConfig · ErrorDiagnosisConfig · LatencyAttributionConfig (4)

Note: TTFTVariabilityConfig · CostPredictabilityConfig는 monitor 수준 자동 집계(≥5 tasks with ttft_ms extra 및 task_type별 토큰 CV). 데코레이터 파라미터 불필요.

전체 실전 예제: Evaluator_Examples/ch03_harness_basics.py


CI/CD 품질 게이팅

코드에서 직접

eval = QuickEval("results/")

@eval.qa
def agent(question, ground_truth=""): ...

# 평가 실행 후
eval.gate(tcr=85, accuracy=70, quality=3.5, hallucination=5)
# 임계값 미달 시 sys.exit(1) — CI 파이프라인 실패 처리

CLI (GitHub Actions)

- name: Run Evaluation
  run: python eval_suite.py --output results/ci.json

- name: Quality Gate
  run: |
    agent-eval gate results/ci.json \
      --tcr 85 --accuracy 70 --p95-latency 3.0 --hallucination 5

agent-eval gate 옵션:

옵션 설명
--tcr N Task Completion Rate 최소값 (%)
--accuracy N 정확도 최소값 (%)
--p95-latency N P95 지연시간 최대값 (초)
--hallucination N 환각 탐지율 최대값 (%)
--llm-judge N LLM Judge 종합 점수 최소값 (0–5)
--fail-on-regression N 이전 기준선 대비 허용 하락 비율 (%)
--junit-xml PATH JUnit XML 출력 (CI 연동)

종료 코드: 0 = 전체 통과 / 1 = 임계값 미달 / 2 = 회귀 감지


조건부 알림

3종 데코레이터 모두 동일한 alert_rules= API를 지원합니다.

from agent_evaluator.decorators import AlertRuleBuilder

slow_rule  = AlertRuleBuilder.when_latency_above(3.0,  handler=lambda msg, tr: print(f"[SLOW] {msg}"))
error_rule = AlertRuleBuilder.when_accuracy_below(0.7, handler=lambda msg, tr: send_slack(msg))
fail_rule  = AlertRuleBuilder.when_completion_below(0.8, handler=lambda msg, tr: send_alert(msg))

# 3종 데코레이터 모두 동일하게 적용
@agent_eval(monitor,      task_type="qa", alert_rules=[slow_rule, error_rule])
def agent(question, ground_truth=""): ...

@batch_eval(monitor,      task_type="qa", alert_rules=[slow_rule])
def batch_agent(questions, ground_truths=None): ...

@conversation_eval(monitor, max_turns=5,  alert_rules=[fail_rule])
def chat(question, session_id="s1"): ...

주기적 자동 저장 (flush_every)

프로세스가 중간에 종료되어도 결과가 보존됩니다. 3종 데코레이터 모두 지원합니다.

@agent_eval(monitor, task_type="qa", flush_every=10)
def agent(question, ground_truth=""): ...

@batch_eval(monitor, task_type="qa", flush_every=5)
def batch_agent(questions, ground_truths=None): ...

# QuickEval에서도 동일
eval = QuickEval("results/", auto_save=True, auto_save_interval=10)

preset — 환경별 설정 묶음

3종 데코레이터 모두 동일한 preset= 파라미터를 지원합니다.

preset 자동 적용 설정 환경
"production" flush_every=50 · enable_anomaly_detection=True · sample_rate=0.1 운영 서버
"development" llm_judge=LLMJudgeConfig() · auto_detect_framework=True 개발·디버깅
"testing" sample_rate=1.0 · timeout=10.0 단위 테스트
"canary" sample_rate=0.01 · flush_every=100 카나리 배포
@agent_eval(monitor,      task_type="qa", preset="production")
@batch_eval(monitor,      task_type="qa", preset="testing")
@conversation_eval(monitor, max_turns=5,  preset="development")

CLI 명령어

명령어 설명
agent-eval init 대화형 API 키 설정 마법사
agent-eval check 현재 설정 상태 및 API 키 확인
agent-eval dashboard [dir] FastAPI 대시보드 웹 서버 실행
agent-eval gate <result.json> CI/CD 품질 게이팅
agent-eval trend <dir> 순차 평가 결과 TCR·정확도 추세 분석 (회귀 감지)
agent-eval dataset build <dir> 운영 결과에서 골든 데이터셋 자동 추출
agent-eval monitor Arize Phoenix + OTEL 실시간 모니터링
agent-eval --version 패키지 버전 출력

평가 결과 출력 시나리오

데코레이터로 수집된 지표를 세 가지 방식으로 출력할 수 있습니다.

시나리오 용도 추가 작업
터미널 출력 즉시 확인 · 디버깅 없음
FastAPI 대시보드 개발·검증 단계 시각화 save_to_file() 후 CLI 실행
Phoenix OTEL 프로덕션 실시간 모니터링 setup_otel() 선언 후 별도 터미널에서 agent-eval monitor

시나리오 1 — 터미널 출력

데코레이터 실행 후 generate_report()로 결과를 즉시 확인합니다.

from agent_evaluator import PerformanceMonitor
from agent_evaluator.decorators import agent_eval

monitor = PerformanceMonitor(output_dir="results/")

@agent_eval(monitor, task_type="qa")
def my_agent(question: str, ground_truth: str = "") -> str:
    return llm.invoke(question)

for q, gt in dataset:
    my_agent(q, ground_truth=gt)

# 터미널 출력 — generate_report() 후 to_json() 또는 to_dict()
report = monitor.generate_report()
print(report.to_json(indent=2))
# → {"accuracy_metrics": {...}, "efficiency_metrics": {...}, "quality_metrics": {...}}

시나리오 2 — FastAPI 대시보드

save_to_file()results/ 에 JSON을 쓰고, agent-eval dashboard가 이를 읽습니다.

# 방법 A: 실행 후 수동 저장
monitor.save_to_file("eval")          # results/eval.json + .html 생성

# 방법 B: auto_save — N건마다 자동 저장
monitor = PerformanceMonitor(output_dir="results/", auto_save=True, auto_save_interval=10)

# 방법 C: QuickEval
eval = QuickEval("results/")
@eval.qa
def my_agent(q, ground_truth=""): ...
eval.save()                           # results/quickeval.json + .html
# 대시보드는 기본 설치에 포함
agent-eval dashboard results/ --watch        # 파일 변경 시 자동 갱신
URL 내용
http://localhost:8765 메인 대시보드
http://localhost:8765/slides 발표용 슬라이드 뷰
http://localhost:8765/api/docs Swagger API 문서

시나리오 3 — Phoenix 실시간 모니터링 (OTEL)

setup_otel()PerformanceMonitor 생성 전에 호출해야 합니다. 이후 모든 record_task() 호출에서 OTLP 스팬이 자동 발행됩니다.

# 터미널 1 — Phoenix 서버 기동 (OTEL은 기본 설치에 포함)
agent-eval monitor                           # http://localhost:6006
# 터미널 2 — 에이전트 코드
from agent_evaluator import setup_otel, PerformanceMonitor
from agent_evaluator.decorators import agent_eval

setup_otel(endpoint="http://localhost:6006", service_name="my-agent")  # ← 반드시 먼저
monitor = PerformanceMonitor(output_dir="results/")

@agent_eval(monitor, task_type="qa")
def my_agent(question: str, ground_truth: str = "") -> str:
    return llm.invoke(question)

# 호출 시 OTLP 스팬 자동 전송 → Phoenix Tracing 탭에서 즉시 확인
my_agent("한국의 수도는?", ground_truth="서울")

Tracing · Evaluators · Datasets · Prompts 4개 메뉴에서 실시간 확인 가능합니다.


공개 API

from agent_evaluator import (
    PerformanceMonitor,            # 평가 오케스트레이터
    QuickEval,                     # 원스톱 Facade
    HybridPerformanceMonitor,      # Layer 3 포함 모니터
    TaskResult, TaskType, EvaluationReport,
    create_taskresult,
    evaluation_session, async_evaluation_session,
    ConversationSession, ConversationMetrics, ConversationTurn,
    LLMJudge,
    SimpleTaskAlertRule, AlertRuleBuilder,
)

from agent_evaluator.decorators import (
    # ── 3종 핵심 데코레이터 ──────────────────
    agent_eval,           # 단일 태스크 (1호출 → 1 TaskResult)
    batch_eval,           # 배치 평가   (1호출 → N TaskResult)
    conversation_eval,    # 멀티턴 대화 (N호출 → 1 TaskResult)

    # ── 통합 팩토리 & 탈출구 ─────────────────
    EvalDecorator,        # 3종 공통 설정 팩토리
    eval_context,         # 데코레이터 불가 시 컨텍스트 매니저

    # ── 메타데이터 & 유틸리티 ────────────────
    EvalMetadata,         # agent_eval / batch_eval 추가 메타데이터
    TurnMetadata,         # conversation_eval 턴별 메타데이터
    get_eval_ctx,         # 스레드 로컬 평가 컨텍스트 접근
    FrameworkLiteral,     # 21개 프레임워크 타입 힌트
    get_framework_info,   # 프레임워크 어댑터 정보 조회
    AlertRuleBuilder,     # 알림 규칙 팩토리
    flush_conversation,   # 대화 세션 수동 종료
    flush_all_conversations,
)

예제 가이드

Book 챕터 기반 26개 파일로 구성됩니다. 각 파일은 독립 실행 가능합니다.

예제별 의존성

예제 챕터 내용 선택
ch01_first_eval.py Ch01 Layer 1 기초 — 정확도·할루시네이션·TCR
ch02_quickstart.py Ch02 QuickEval 5분 첫 평가
ch03_harness_basics.py Ch03 Harness Gate A–G 7개 개요 agent-eval monitor
ch04_group_a.py Ch04 Gate A: Goal Achievement (6개 Config)
ch05_group_b.py Ch05 Gate B: Behavioral Integrity (6개 Config)
ch06_group_c.py Ch06 Gate C: Reliability (5개 Config)
ch07_group_d.py Ch07 Gate D: Performance Contract (5개 Config)
ch08_group_e.py Ch08 Gate E: Security Boundary (3개 Config)
ch09_group_f.py Ch09 Gate F: Multi-Agent Coordination (4개 Config)
ch10_group_g.py Ch10 Gate G: Observability + AnomalyDetector · CostTracker
ch11_eval_data.py Ch11 평가데이터 설계 — GoldenSetBuilder · evaluation_session
ch12_decorators.py Ch12 데코레이터 완전정복 — @agent_eval · @batch_eval · QuickEval · LLMJudge
ch13_frameworks.py Ch13 프레임워크 통합 — LangChain · LangGraph · CrewAI · AutoGen agent-evaluator[langchain] (선택)
ch14_thresholds.py Ch14 임계값 설정과 품질 기준 수립
ch15_dashboard.py Ch15 대시보드 시각화 — QuickEval · AnomalyDetector · CostTracker 데이터 생성 agent-eval dashboard
ch16_alerts.py Ch16 알림시스템 — StreamingEvaluator · AlertEngine · SimpleTaskAlertRule SLACK_WEBHOOK_URL (미설정 시 Mock)
ch17_weekly_review.py Ch17 주간·월간 품질 리뷰 자동화
ch18_cicd_gate.py Ch18 CI/CD 품질 게이팅 — Harness 최소 검증 · exit 0/1
ch19_phoenix.py Ch19 Phoenix OTEL — Tracing · Datasets · GraphQL + DeepEval · Ragas agent-evaluator[eval] + OPENAI_API_KEY (선택)
ch20_deployment.py Ch20 프로덕션 배포전략 — v1 vs v2 Gate 점수 비교
ch21_pipeline.py Ch21 종합 실무파이프라인 — 개발→CI→운영→개선 4단계
ch22_project_analysis.py Ch22 기존 프로젝트 해부 — 토폴로지·LLM 열거·위험 우선순위화
ch23_gate_mapping.py Ch23 Gate 매핑 전략 — 실패모드 카탈로그 → Config 번역 + 가중치 설계
ch24_quickeval_entry.py Ch24 첫 번째 이식 — 침습도 Level 0/1 패턴 + 첫 측정값 획득
ch25_harness_full.py Ch25 전체 통합 — 중앙 모니터 + 어댑터 + 보안 스캔 + Gate F 버그 발견
ch26_cicd_weekly.py Ch26 CI/CD 완성 — 골든 데이터셋·추세 분석·주간 리뷰·비용 드리프트

실행

cd Evaluator_Examples

python ch01_first_eval.py      # Layer 1 기초 — Accuracy · Hallucination · Quality · Latency · Token · TCR
python ch02_quickstart.py      # QuickEval 5분 첫 평가
python ch03_harness_basics.py  # Harness Gate A–G 개요 — 7개 Gate · 33개 Config
python ch04_group_a.py         # Gate A: Goal Achievement — InstructionConfig · GoalAlignmentConfig 외
python ch05_group_b.py         # Gate B: Behavioral Integrity — LoopDetectionConfig · StateConsistencyConfig 외
python ch06_group_c.py         # Gate C: Reliability — ReproducibilityConfig · FaultToleranceConfig 외
python ch07_group_d.py         # Gate D: Performance Contract — SLAConfig · TTFTVariabilityConfig 외
python ch08_group_e.py         # Gate E: Security Boundary — ThreatSeverityConfig · ComplianceConfig 외
python ch09_group_f.py         # Gate F: Multi-Agent Coordination — ConsensusConfig · AgentRoleConfig 외
python ch10_group_g.py         # Gate G: Observability + AnomalyDetector · CostTracker
python ch11_eval_data.py       # 평가데이터 설계 — GoldenSetBuilder · evaluation_session
python ch12_decorators.py      # 데코레이터 완전정복 — @agent_eval · @batch_eval · QuickEval · LLMJudge
python ch13_frameworks.py      # 프레임워크 통합 — LangChain · LangGraph · CrewAI · AutoGen
python ch14_thresholds.py      # 임계값 설정과 품질 기준 수립
python ch15_dashboard.py       # 대시보드 시각화 데이터 생성
python ch16_alerts.py          # 알림시스템 — StreamingEvaluator · AlertEngine
python ch17_weekly_review.py   # 주간·월간 품질 리뷰 자동화
python ch18_cicd_gate.py       # CI/CD 품질 게이팅
python ch19_phoenix.py         # Phoenix OTEL + DeepEval · Ragas (opt-in)
python ch20_deployment.py      # 프로덕션 배포전략
python ch21_pipeline.py        # 종합 실무파이프라인
python ch22_project_analysis.py  # 기존 프로젝트 해부 4단계
python ch23_gate_mapping.py    # Gate 매핑 전략
python ch24_quickeval_entry.py # 첫 번째 이식 — Level 0/1 침습
python ch25_harness_full.py    # 전체 통합 파이프라인
python ch26_cicd_weekly.py     # CI/CD 완성 + 주간 리뷰

# ── 인프라 ───────────────────────────────────────────────────
agent-eval monitor             # Phoenix 서버 기동 (http://localhost:6006)
agent-eval dashboard --watch   # 대시보드 (http://localhost:8765)

구 11개 예제(01~08, 09, 10)는 Evaluator_Examples/.deprecated/ 에 보존됩니다.


프로젝트 구조

agent-evaluator/
├── agent_evaluator/
│   ├── decorators.py            # agent_eval · batch_eval · conversation_eval
│   │                            # EvalDecorator · eval_context · EvalMetadata · TurnMetadata
│   ├── quick_eval.py            # QuickEval — 원스톱 Facade
│   ├── core/
│   │   ├── trackers/
│   │   │   ├── base.py          # TaskResult · EvaluationReport · TaskType
│   │   │   ├── layer1.py        # Foundation 지표 6종
│   │   │   ├── layer2.py        # Agentic 지표 5종
│   │   │   ├── security.py      # 보안 지표 5종 (Layer 2-B)
│   │   │   ├── monitor.py       # PerformanceMonitor (오케스트레이터)
│   │   │   ├── conversation.py  # ConversationSession · ConversationMetrics
│   │   │   └── feedback.py      # ImplicitFeedbackTracker
│   │   ├── otel/                # OpenTelemetry 통합 (기본 설치에 포함)
│   │   ├── hybrid_monitor.py    # HybridPerformanceMonitor
│   │   └── monitor_context.py   # evaluation_session · async_evaluation_session
│   ├── integrations/
│   │   ├── llm_judge.py         # LLMJudge
│   │   └── metric_adapters.py   # DeepEval · Ragas 어댑터
│   ├── serve/                   # FastAPI 대시보드 (기본 설치에 포함)
│   ├── cli/                     # agent-eval CLI
│   ├── alerts/                  # AlertEngine · SimpleTaskAlertRule
│   ├── anomaly/                 # AnomalyDetector
│   ├── cost/                    # CostTracker · AdaptivePolicy
│   └── datasets/                # GoldenSetBuilder
│
├── Evaluator_Examples/          # 예제 26개 파일 (ch01~ch26, .deprecated/에 구 11개 보존)
├── tests/                       # 2,465개+ 테스트 함수, 53개 파일
└── pyproject.toml

의존성 명세

기본 설치 포함 패키지 (pip install agent-evaluator)

패키지 버전 범위 용도
numpy ≥1.20.0, <3.0.0 수치 연산
pandas ≥1.3.0, <4.0.0 지표 집계
python-dotenv ≥0.19.0, <2.0.0 환경변수 관리
openai ≥1.0.0, <3.0.0 LLMJudge 엔진
anthropic ≥0.20.0, <1.0.0 LLMJudge 엔진
fastapi ≥0.110.0, <1.0.0 웹 대시보드
uvicorn[standard] ≥0.29.0, <1.0.0 웹 대시보드
jinja2 ≥3.1.0, <4.0.0 웹 대시보드
python-multipart ≥0.0.9, <1.0.0 웹 대시보드
opentelemetry-sdk ≥1.20.0, <2.0.0 OTEL 모니터링
opentelemetry-exporter-otlp-proto-http ≥1.20.0, <2.0.0 OTEL 모니터링
arize-phoenix ≥7.0.0 Phoenix 실시간 모니터링
pdfplumber ≥0.10.0, <1.0.0 한국어 RAG PDF 처리

선택 extras (설치 명령은 ## 설치 참조)

Extra 주요 패키지 설치 시간 비고
[examples] 기본 + eval 무거움 예제 01~06: 기본만 필요 · 07: eval 추가 필요
[eval] deepeval ≥3.0, <4.0 · ragas ≥0.4, <2.0 · datasets ≥4.0, <6.0 무거움 DeepEval/Ragas 외부 평가
[langchain] langchain ≥1.0, langgraph ≥1.0 중간 사용자 LangChain 에이전트 코드용¹
[dspy] dspy-ai ≥2.0 중간 사용자 DSPy 에이전트 코드용¹
[pydanticai] pydantic-ai ≥1.0, <2.0 빠름 사용자 PydanticAI 에이전트 코드용¹
[crewai] crewai ≥1.0, <2.0 무거움 (단독 격리) 사용자 CrewAI 에이전트 코드용¹
[autogen] pyautogen ≥0.3, autogen-agentchat ≥0.4 무거움 (단독 격리) 사용자 AutoGen 에이전트 코드용¹
[full] 기본 + eval + langchain + dspy + pydanticai + crewai + autogen 매우 무거움 ⚠️ 10분+, CI 전체 호환성 검증용
[dev] pytest · pytest-cov · ruff · mypy · build · twine 빠름 개발 환경

¹ agent-evaluator 자체는 이 패키지 없이도 완전히 동작 (duck typing). 사용자의 에이전트 코드가 해당 프레임워크를 직접 import할 때만 설치.


개발 환경

git clone https://github.com/bullpeng72/Agent-Evaluator.git
cd Agent-Evaluator
pip install -e ".[dev]"

pytest                          # 테스트 실행 (2,465개+)
ruff check agent_evaluator/    # 린트
ruff format agent_evaluator/   # 포맷
mypy agent_evaluator/          # 타입 검사

변경 이력

v0.8.5 (2026-04-23) — SDK 버그 수정 · Book API 오류 전면 교정

  • eval_efficiency() dict 타입 tokens_used 묵살 버그 수정
  • EfficiencyConfig cost_unit/target_cost_per_completion 설계 오류 수정 (USD→tokens 스케일)
  • CostPredictabilityConfig — 에이전트별 task_type 분리로 CV 격리, Gate D 0.640→0.876
  • ch10_group_g.pyEvalMetadata(extra={...}) 주입 경로 수정, Gate G warn→pass
  • Book 전반 API 오류 교정: AnomalyDetector.scan(), AdaptivePolicy 실제 생성자, EfficiencyConfig 스케일

v0.8.4 (2026-04-21) — 예제 파일 Book 챕터 기반 전면 재편

  • 예제 파일 11개 → 17개 chXX_topic.py 챕터 기반 네이밍으로 전면 재편
  • ch05, ch07, ch10, ch02에 누락 트래커(WorkflowExecution·Latency·TokenEconomy·AnomalyDetector·CostTracker) 추가
  • Phoenix service_name 및 결과 파일명 챕터 번호 기준 동기화
  • Book 27개 마크다운 # 출처: 참조 신규 파일명으로 일괄 갱신
  • ch05_group_b.py create_taskresult 임포트 누락 버그 수정

v0.8.3 (2026-04-21) — LLMJudge 안정성 강화 · Gate 개선 · 보안 트래커 확장

  • LLMJudge 연속 오류 자동 비활성화 (3회 연속 실패 → reset_errors()로 복구)
  • faithfulness 누락 시 None 저장 — 점수 오염 방지
  • AGENT_EVALUATOR_JUDGE_PROVIDER 환경변수 도입 (auto / openai / anthropic)
  • GoalAlignmentConfig · PlanConfigllm_blend_weight 추가 (LLM-rule 혼합 비율, 기본 0.5)
  • LLMJudge.ajudge() 비동기 메서드 추가
  • LLMJudgeConfig.sample_rate 데코레이터 전달 버그 수정
  • agent-eval gate --min-gate-score / --group-weights — Gate A–G 가중 복합 점수 판정
  • agent-eval trend 비용 추세 분석 (total_cost, --fail-on-regression 연동)
  • OutputLeakageDetector(excluded_unix_paths=[...]) — 시스템 경로 제외 목록 커스터마이즈
  • 보안 트래커 sample_rate 파라미터 추가 (고트래픽 성능 최적화)
  • Group B deadlock_by_type 분류 · Gate D insufficient_data_warnings 추가
  • LLMJudge(escalation_model=..., escalation_threshold=2.5) — 다중 모델 자동 에스컬레이션

v0.8.2 (2026-04-17) — Harness Config 33개 양식 통일 · 대시보드 UI 개선

  • Harness Config 카드 33개 아이콘·수식·임계값 배지 양식 통일; 08_harness_eval.py 예제 추가
  • 대시보드 Nav 3단 계층 재편; Gate 상관 히트맵(7×7 Pearson) · 실패 연쇄 추적 추가
  • HTML 리포트 Gate A–G 중심 전면 재편; CSV export Gate 컬럼 16개 추가
  • 그룹 분류 수정: StateConsistencyConfig·DeadlockConfig Group F→B 이동
  • 테스트 파일 2개 추가 (52개 파일, 2,465개+)

v0.8.1 (2026-04-14) — 데코레이터 파라미터 구조화

  • RetryConfig · LLMJudgeConfig · SecurityConfig 3개 구조체 도입; 개별 파라미터 제거
  • enable_hallucinationenable_hallucination_detection 이름 통일
  • 테스트 548개 추가; 파일 72→49개 리구조화

v0.8.0 (2026-04-13) — 정확도 지표 전면 개선

  • Token Overlap F1(조화평균) 교체; Char Similarity Levenshtein 통일
  • task_type 인식 completion_score: code_generation AST 파싱, tool_use 미사용 시 0.6

v0.7.9 (2026-04-13) — RunTrendAnalyzer · arize-phoenix 호환 수정

  • RunTrendAnalyzer + agent-eval trend — 추세 분석 · --fail-on-regression CI/CD 연동
  • arize-phoenix 버전 제약 충돌 수정

v0.7.8 (2026-04-12) — SDK 기본 내장

  • pip install agent-evaluator 단독으로 LLMJudge · 대시보드 · OTEL 사용 가능

v0.7.7 (2026-04-11) — 데코레이터 버그 수정 · 스레드 안전성

  • agent_eval preset 파라미터 미적용 버그 수정; Layer 2 트래커 5개 threading.Lock 추가

v0.7.6 (2026-04-10) — LLMJudge G-Eval/Ragas 대체

  • judge_criteria G-Eval 커스텀 채점; rag_mode=Truefaithfulness 자동 추가

v0.7.0–v0.7.5 (2026-04-01~09) — OTEL/Phoenix · 3종 데코레이터 · QuickEval

  • agent-eval monitor CLI · Arize Phoenix 실시간 모니터링
  • 3종 데코레이터 완성(agent_eval·batch_eval·conversation_eval) · QuickEval Facade
  • 21개 프레임워크 어댑터 · 보안 트래커 실동작 버그 수정(CRITICAL)

v0.6.x (2026-03-21~04-01) — SDK 안정화

  • LangChain/LangGraph/CrewAI/AutoGen · FastAPI 대시보드 · LLMJudge · ConversationSession

v0.2.x–v0.5.x — 초기 구현

  • Layer 1/2/3 트래커 25개 · evaluation_session 초기 구현

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

agent_evaluator-0.9.0.tar.gz (843.6 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

agent_evaluator-0.9.0-py3-none-any.whl (867.9 kB view details)

Uploaded Python 3

File details

Details for the file agent_evaluator-0.9.0.tar.gz.

File metadata

  • Download URL: agent_evaluator-0.9.0.tar.gz
  • Upload date:
  • Size: 843.6 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.14

File hashes

Hashes for agent_evaluator-0.9.0.tar.gz
Algorithm Hash digest
SHA256 0932e7184118d3aef23b28ba471951104aab40d7472867deec9f1053cc920ace
MD5 ca649165dced774c3f2967bf6d3d58c7
BLAKE2b-256 060f9b2308b169bddb2301f82cc07019b8a9bf0a12550753fe614785d7559fb9

See more details on using hashes here.

File details

Details for the file agent_evaluator-0.9.0-py3-none-any.whl.

File metadata

  • Download URL: agent_evaluator-0.9.0-py3-none-any.whl
  • Upload date:
  • Size: 867.9 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.11.14

File hashes

Hashes for agent_evaluator-0.9.0-py3-none-any.whl
Algorithm Hash digest
SHA256 9fc1838dac6d67af99837452f3bc49d77268a550cdfd03ff1247acaa7a4e586e
MD5 681b1e0eb9e51b6056c791e5f2bd2a6a
BLAKE2b-256 82a3728bfda2b76c661b6a788235ffd1b34ec6807c68371e1bb5e65cdb22cee9

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page