Надёжность: эскалация, ошибки, multi-pass review
Цель: спроектировать паттерны, которые делают агентов **production-ready**. Это Домен 5 экзамена (15%), но встречается в каждом сценарии.
Эскалация — когда человек нужен
4 триггера эскалации
- Пользователь явно просит — "connect me to a human", "talk to someone real"
- Исключения/пробелы в политике — ситуация не предусмотрена правилами
- Невозможность продвинуться — агент застрял, не может завершить
- Критически неопределённый случай — ставки высоки, уверенность низкая
Плохо: оценки на основе самооценки уверенности
# НЕ ДЕЛАЙ
if model_confidence < 0.5:
escalate()LLM плохо калиброваны — они уверены когда не должны быть, и неуверены когда всё ок. Самооценка уверенности ненадёжна.
Плохо: анализ настроения
# НЕ ДЕЛАЙ
if customer_sentiment == "frustrated":
escalate()Фрустрация не коррелирует со сложностью случая. Счастливый клиент может иметь проблему которая вне политики. Расстроенный — может иметь простой запрос.
Хорошо: явные критерии + few-shot
ESCALATE when:
- Customer explicitly requests human
- Refund amount > $500 (policy limit)
- Account has been flagged for fraud review
- Multiple previous escalations (pattern indicator)
- Policy is ambiguous on this specific case type
Examples of WHEN to escalate:
[example 1: user asks "I want to speak to a manager"]
[example 2: damaged item, photo evidence, standard policy replacement — DO NOT escalate]
[example 3: damaged item, photo evidence, UNUSUAL case (product discontinued) — escalate]
Конкретные критерии + демонстрация на примерах. Это решение корневой причины — нечёткие границы принятия решений.
Немедленная эскалация на явный запрос
Если клиент говорит "I want to talk to a human" — не пытайся решить самостоятельно сначала. Эскалируй сразу.
Попытка решить когда пользователь явно попросил человека = ухудшение опыта.
Запрос дополнительных идентификаторов
Сценарий: клиент пишет "check my order", но в системе 3 заказа с его именем.
Плохо: эвристика (взять последний? первый? большой?) Хорошо: спросить
I see multiple orders associated with your account:
- Order #12345 (2026-04-10, $129)
- Order #12346 (2026-04-08, $45)
- Order #12340 (2026-03-22, $280)
Which one are you asking about?
Эвристика при множественных совпадениях ведёт к ошибкам которых можно было избежать простым уточнением.
Распространение ошибок в multi-agent системах
Антипаттерн: унифицированные статусы
# Все подагенты возвращают либо success, либо "search unavailable"
def search_agent():
try:
return search()
except:
return {"status": "search unavailable"}Координатор теряет всю полезную информацию. Не может решить как восстанавливаться.
Антипаттерн: тихое подавление
# Плохо — ошибка пропадает, возвращается пустота
def search_agent():
try:
return search()
except:
return {"results": []} # выглядит как успех с нулём результатовЕщё хуже — координатор думает "результатов не нашлось, всё ок". А на самом деле сервис упал.
Антипаттерн: полное завершение процесса при единичном сбое
# Плохо — один подагент упал, всё отменяется
try:
a_results = agent_a()
b_results = agent_b()
c_results = agent_c()
except:
raiseДаже если 2 из 3 вернули полезные данные — теряем всё.
Паттерн: структурированный контекст ошибки
def search_agent():
try:
results = search()
return {"success": True, "results": results}
except TimeoutError as e:
return {
"success": False,
"error_type": "timeout",
"attempted_approach": "semantic search",
"partial_results": partial, # если есть
"alternatives": ["try keyword search", "reduce scope"],
"is_retryable": True
}
except ServiceUnavailable as e:
return {
"success": False,
"error_type": "service_down",
"retry_after": 30,
"is_retryable": True
}
except ValidationError as e:
return {
"success": False,
"error_type": "validation",
"details": str(e),
"is_retryable": False # повтор не поможет
}Координатор получает контекст для интеллектуального восстановления:
- Временная ошибка? Повтори
- Нет доступа? Эскалируй
- Валидация? Не повторяй
Локальное восстановление vs эскалация
# В подагенте — локальный retry для transient
if error_type == "transient" and attempt < 3:
return retry_with_backoff()
# Если не разрешилось за 3 попытки — пропагируй координатору
return structured_error_contextTransient ошибки лечатся локально. Пропагируются только неразрешимые.
Multi-pass review
Проблема однопроходного ревью больших PR
14 файлов в PR. Single-pass review:
- Детальная обратная связь по одним файлам
- Поверхностная по другим
- Пропуск явных багов
- Противоречивые замечания (паттерн помечен как проблема в одном файле, одобрен в другом)
Корневая причина: размытие внимания. Модель не может одинаково глубоко обработать все 14 файлов за раз.
Паттерн: разделить на проходы
Pass 1: Per-file local analysis
→ File A: issues specific to File A
→ File B: issues specific to File B
→ ...
Pass 2: Cross-file integration analysis
→ Data flow between files
→ Interface contracts
→ Shared state mutations
Пофайловый анализ глубокий (фокус узкий). Интеграционный — отдельный проход с другим вопросом ("как эти файлы взаимодействуют?").
Это НЕ о контекстном окне
Переключение на модель с большим контекстным окном (1M) не решает проблему размытия внимания. Дело не в том сколько текста помещается, а в том как глубоко модель его обрабатывает.
Multi-instance review (независимые проходы)
Для критических решений:
review_a = claude.call(task, system="You are reviewer A")
review_b = claude.call(task, system="You are reviewer B") # новая сессия, чистый контекст
merged = synthesize(review_a, review_b)Независимые инстансы (без предшествующего контекста рассуждений) эффективнее ловят тонкие ошибки, чем самопроверка. Модель сохраняет контекст рассуждений от генерации — это снижает вероятность оспорить собственное решение.
Антипаттерн: консенсус как критерий
# Плохо — пропустим реальные баги где только один reviewer заметил
if not (reviewer_a_found and reviewer_b_found):
skip_issueИщи объединение (flag if any reviewer found), не пересечение.
Human-in-the-loop калибровка
Риск: агрегированная метрика маскирует слабые места
97% точности на извлечении из документов — отлично? Проверь разбивку:
- 99% на invoices
- 99% на receipts
- 75% на рукописных документах
Общая точность 97% маскирует слабость на рукописных. В проде ты получишь взрывной рост ошибок когда 30% твоих документов окажутся рукописными.
Паттерн: стратифицированная валидация
Периодически сэмплируй высокоуверенные извлечения по каждому типу документа и полю, вручную проверяй. Если точность по типу падает — направляй этот тип на human review.
Confidence per field
{
"invoice_number": {"value": "INV-12345", "confidence": 0.99},
"total_amount": {"value": 129.00, "confidence": 0.98},
"tax_amount": {"value": 12.90, "confidence": 0.72}
}Поле-level uncertainty → маршрутизация только неуверенных полей на human review. Уверенные — автообработка.
Практика (30 минут)
Задача 1. Audit текущей системы
Если у тебя есть agent-система в проде:
- Что она делает при таймауте подагента? (шанс что ответ — "тихо проглатывает")
- Какие триггеры эскалации? (шанс что ответ — "нет формальных")
- Есть ли multi-pass для критичных ревью?
Задача 2. Спроектировать эскалацию
Для твоего use-case (поддержка/ревью/extract) напиши:
- 5+ явных триггеров эскалации
- 3+ few-shot примера "escalate vs handle"
- Политика "immediate escalation" на явный запрос
Задача 3. Структурированные ошибки
Перепиши один подагент чтобы возвращал структурированный контекст ошибок (error_type, retryable, partial_results, alternatives).
Что дальше
Последний урок — подготовка к Claude Certified Architect. Разбираем формат экзамена, 5 доменов, рекомендации по подготовке.