
자율형 AI 에이전트 「업계 특화」(Gov·지자체, SaaS, EC) & RAG를 스크래치로 제작했습니다.
요약
공통 엔진을 기반으로 업종별 프로파일(Gov, SaaS, EC)을 주입하여 특화된 성능을 내는 자율형 AI 에이전트와 RAG 시스템 구현 방법을 소개합니다. 업종별 검색 범위, 답변 엄격도, 에스컬레이션 로직 등을 차별화하여 실서비스 적용 가능성을 높였습니다.
핵심 포인트
- 공통 엔진에 업종별 프로파일을 적용하는 설계 사상 제시
- 2단계 판정 로직을 통한 FAQ와 실제 의뢰의 정교한 구분
- HITL(Human-in-the-loop) 및 본인 확인 절차를 통한 안전한 액션 수행
- KPI 기반의 성능 측정 및 개선 프로세스 공유
【NEW】자율형 AI 에이전트・업계 특화(Gov·지자체, SaaS, EC) & RAG

1. 서론
일본어 RAG 자율형 AI 에이전트(GRACE・자작)를 토대로 한, 고객 지원 / 사내 지식 코파일럿(Copilot)의 업계 특화 버전을 스크래치로 제작했습니다. 대상은 Gov(지자체) / SaaS / EC의 3개 업종입니다.
설계 사상은 한 줄로 말할 수 있습니다.
"공통 엔진은 하나, 교체되는 것은 프로파일뿐"
--vertical {gov|saas|ec}
를 통해 업계 프로파일(VerticalProfile)을 적용하고, 다음 6개 축을 업종별로 전환합니다.
- 검색 범위(
allowed_collections): 답변의 근거로 삼아도 좋은 지식을 해당 업계의 컬렉션으로 한정 - 답변의 엄격함 (임계값): Gov는 "틀릴 바에는 창구로 안내하자" = 3개 업종 중 유일하게
0.8/0.5로 엄격화 - 강제 에스컬레이션(Escalation) 키워드 × 2단계 판정: 키워드 후보 검출(제1단계) + 경량 LLM 의도 분류(제2단계)를 통해, "감면 제도의 개요를 알려줘" (FAQ)는 답변하고, "감면을 개별적으로 판단해 줘" (의뢰)는 사람에게 전달 — 잘못된 에스컬레이션 및 오기입 억제
- 액션(Action): 결함·반품 등의 의뢰를 HITL (CONFIRM 승인)을 경유하여 기입 (기본값은 안전한 드라이 런(Dry-run). Webhook 실연동 대응)
- 본인 확인: EC만
require_identity=True(주문 조작은 본인 확인 → 승인 → 실행 순서로 진행, 미확인 시 유인 대응) - KPI 자동 측정:
eval/vertical/run.py로 분기 일치율·오에스컬레이션율·출처 부여율·본인 확인 준수율 등을 측정
답변에는 반드시 출처를 붙이며, 근거가 부족하면 Web 폴백(Fallback)으로 사실 확인을 하여 내부 × Web을 상호 검증합니다. 그래도 부족하면 "모르겠습니다"라고 성실하게 답하고 유인 대응으로 에스컬레이션합니다.
이 기사에서 알 수 있는 내용은 다음 3가지입니다.
- 업계 특화 설계와 구현 — 공통 엔진은 하나로 유지하면서, 업종별 차이점을 "프로파일"로서 주입하는 방법 (실제 코드 포함)
- 2가지 판정 로직 — "환불 정책을 알려줘" (FAQ)와 "환불해 줘" (의뢰)를 구분하는 2단계 판정과, 성실한 "찾을 수 없습니다"를 사람에게 넘기는 정보 없음 검지
- KPI 기반의 개선 기록 — 분기 일치율 0.857~0.889에서 1.000에 도달하기까지 무엇이 실패했고 어떻게 수정했는가
대상 독자는 RAG 챗봇을 업무에 도입하려는 엔지니어 및 "PoC는 작동했지만 오답이 두려워 실서비스에 내놓지 못하는" 단계의 팀입니다.
모든 소스를 공개하고 있습니다.
- Claude API 버전 (본 기사의 구현): https://github.com/nakashima2toshio/anthropic_grace_agent_v2
- 로컬 LLM 버전 (Ollama·온프레미스용): https://github.com/nakashima2toshio/ollama_grace_agent_v2
업계 특화 문서 목록 (본 기사의 상세 버전·리포지토리 내):
| # | 문서 | 설명 |
|---|---|---|
| 1 | docs/agent_support_example.md | GRACE-Support 본체의 IPO 사양 — 전체 아키텍처(Architecture)·①Plan~⑦응답 데이터 플로우(Data Flow)·클래스/함수 상세·CLI/프로그램 사용 예시 |
| 2 | docs/vertical_comparison.md | 3개 업계의 병렬 비교 — 성격·7개 기구·6개 축·2단계 판정의 충돌 어휘·검색 스코프(Scope) 설계·데이터 전략·KPI 8개 관점 대비 + 전체 대비도 |
| 3 | docs/vertical_gov.md | Gov·지자체 프로파일 — 유일한 엄격 임계값(0.8/0.5)·감면/불복 trap의 오탐 억제·e-Gov 법령 API 투입 절차·KPI 7/7 |
| 4 | docs/vertical_saas.md | SaaS 프로파일 — 에스컬레이션(Escalation) 용어 7개(최다)·과금/SLA trap·결함 티켓 생성·OSS docs 투입·KPI 7/8 |
| 5 | docs/vertical_ec.md | EC 프로파일 — 유일한 require_identity=True (본인 확인 플로우)·반품/환불/해지 trap·KPI 9/9 |
2. 왜 「업계 특화」가 필요한가
범용 RAG+AI-Agent를 업무 지원에 배치하면, 두 종류의 실패가 발생합니다.
실패 1: 답해서는 안 되는 질문에 답해버린다.
"고정자산세 감면을 개별적으로 판단해 달라"는 상담에, 봇이 일반론으로 답해버리는 경우입니다. 행정의 개별 판단·EC의 결제 트러블·SaaS의 장애 보고는 애초에 기계가 답해도 되는 주제가 아닙니다.
실패 2: 답해도 되는 질문을 사람에게 넘겨버린다.
반대로, 위험한 단어를 키워드로 걸러내는 단순한 대책을 세우면, "주민세 감면 제도의 개요를 알려줘"와 같은 단순 FAQ 질문까지 유인 대응(Human-in-the-loop)으로 넘어가게 되어 자동화의 의미가 없어집니다.
즉, "답해도 되는 것 / 사람에게 넘길 것"의 경계선은 업종마다 다르며, 심지어 단어만으로는 구분할 수 없습니다. 이 경계선을 업종별로 정의하여 구현한 것이 본 프로젝트의 「업계 특화」입니다.
3. 아키텍처 — GRACE(자작 모듈) -Support의 파이프라인
토대가 되는 에이전트(GRACE-Support)는 다음의 7단계 + 1 게이트 파이프라인으로 구성됩니다.
실행 예시:
python agent_support_example.py --vertical gov "주민표 사본 발급 방법은?"
요점은 세 가지입니다.
- 답변에는 반드시 출처를 붙이며, 답변의 각 주장이 출처에 의해 뒷받침되는지(Groundedness)를 LLM으로 검증합니다. - 근거가 부족하면 Web에서 교차 검증하고, 그래도 부족하면 "모릅니다"라고 답하며 **유인 대응으로 에스컬레이션(Escalation)**합니다. - 부작용이 있는 조작(티켓 생성·답장)은 사람의 승인(HITL, Human-in-the-loop)을 거친 후 실행합니다. 기본값은 안전한 드라이 런(Dry run)입니다.
기술 스택(Tech Stack)은 LLM이 Anthropic Claude(판정계는 경량 모델인 claude-haiku-4-5-20251001), Embedding이 Gemini(gemini-embedding-001), 벡터 DB가 Qdrant입니다. 파이프라인 본체의 상세 내용은 docs/agent_support_example.md에 맡기고, 본 기사는 「업계 특화」의 설계와 구현에 집중합니다.
4. 업계 특화의 정의 — 공통 엔진 하나, 교체하는 것은 프로파일뿐
이 엔진은 gov/SaaS/EC에서 완전히 공통입니다. 업종의 차이는 모두 다음 VerticalProfile(dataclass)의 차이분으로서 주입됩니다.
@dataclass
class VerticalProfile:
name: str # 프로파일 표시 이름
...
CLI에서는 --vertical {gov|saas|ec}를 붙이는 것만으로 전환됩니다. 다시 말해, 업계 특화의 실체는 다음 6개 축을 업종별로 정의한 것입니다.
① 무엇을 지식원으로 삼고, ② 어디까지 자신감이 있으면 답하며, ③ 무엇을 인간에게 넘기고, ④ 무엇을 실행하며, ⑤ 어떻게 말하고, ⑥ 무엇으로 측정할 것인가
이 6개 축은 구현상 7개의 기구에 대응합니다. "프로파일의 어떤 항목이 파이프라인의 어디에서 작용하는가"를 표로 나타내면 다음과 같습니다.
| # | 기구 | 업종별로 무엇이 변하는가 | 구현 위치 |
|---|---|---|---|
| 1 | 검색 스코프 (collections) | 답변의 근거로 삼아도 되는 지식(Knowledge)의 범위. 폴백(Fallback) 검색도 업종 외로 유출되지 않음 | RAGSearchTool._apply_allowed_collections |
| 2 | 답변의 엄격함 (임계값) | 어느 정도의 확신이 있어야 답변해도 되는가 | _answer_gate() |
| 3 | 강제 에스컬레이션 기준 (에스컬레이션 단어 × 의도 분류) | 기계가 답변해서는 안 되는 화제의 정의 | _should_force_escalate() |
| 4 | 액션 어휘 (action_map) | 「대응」으로 간주하는 의도와 그 처리 대상 | _decide_action() |
| 5 | 본인 확인 (require_identity) | 부수 효과(Side-effect)가 있는 조작 전에 본인 확인이 필요한가 | _perform_action() |
| 6 | 업무 방침 (prompt_addendum) | 답변의 말투·금칙 사항. 프롬프트의 시스템 지시(System Instruction) 직후에 주입 | ReasoningTool._build_prompt() |
| 7 | 평가 기준 (KPI · 테스트 질문) | 무엇을 좋은 서포트로 볼 것인가 | eval/vertical/ |
프로파일의 각 항목이 파이프라인의 어디에 영향을 미치는지 도식화하면 다음과 같습니다.
설계 이유 (Trade-off)
「업종마다 별도의 앱을 만든다」는 선택지도 있었지만, 채택하지 않았습니다. 답변 엔진, 출처 검증, HITL(Human-in-the-Loop)이라는 어려운 공통 부분을 단 한 번만 만들고, 업종 추가를 설정의 추가로 귀결시키기 위해서입니다. 실제로 4번째 업종을 추가하는 작업은 프로파일을 하나 작성하고 지식(Knowledge)을 등록하는 것뿐입니다.
대가도 따릅니다. 프로파일은 「숫자 2개와 일본어 한 문장, 그리고 어휘 리스트」로 구성되므로, 특화의 깊이는 투입된 데이터의 질에 의존합니다. 이 점은 제10장에서 솔직하게 평가하겠습니다.
5. 구현 — 3개 업종의 차이점은 이 3개 블록뿐
이 부분이 본 기사의 핵심입니다. 「공통 엔진 하나, 차이점은 프로파일뿐」임을 실제 코드로 보여드리겠습니다.
5.1 3개 업종의 프로파일 정의 (실제 코드)
agent_support_example.py의 PROFILES는 업종마다 VerticalProfile을 하나씩 가질 뿐입니다. 아래의 3개 블록이 업종 특화 실체의 거의 전부입니다.
# gov: 「틀릴 바에는 창구로 안내하라". 3개 업종 중 유일하게 임계값을 엄격화
"gov": VerticalProfile(
name="지자체",
...
철학이 그대로 설정값에 나타나 있는 것을 알 수 있습니다. gov는 notify_th=0.8(확신이 약한 답변을 내놓을 바에는 창구로 안내)이며, EC는 require_identity=True(지켜야 할 것은 주문 정보의 안전)입니다. 지켜야 할 것이 업종마다 다르기 때문에, 작동하는 기구도 다른 것입니다.
한 줄 요약 비교:
| 구분 | gov (지자체) | SaaS | EC |
|---|---|---|---|
| 성격 | 틀릴 바에는 창구로 안내 | 기술 FAQ는 자동, 장애·과금은 즉시 사람에게 | 절차는 자동화, 주문 정보에는 본인 확인 |
| 가장 두려워하는 실패 | 근거 없는 행정 답변 | 장애·과금 트러블의 놓침 | 본인 확인 없는 주문 조작 |
| 3개 업종 중 유일한 특징 | 임계값 엄격화 (0.8/0.5) | 에스컬레이션 단어가 최다 (7개) | require_identity=True |
_apply_allowed_collections
5.2 검색 스코프의 한정 — --vertical 지정 시, run_support_agent()가 config.qdrant.allowed_collections = profile.collections를 설정하며, RAGSearchTool이 명시적 지정 및 폴백(Fallback) 체인을 포함한 모든 검색 후보에 대해 허용 리스트를 적용합니다 (grace/tools.py::_apply_allowed_collections). 동작은 세 가지 안전장치를 가집니다.
- 부분 일치:
"wikipedia_ja"는"wikipedia_ja_5per"와도 일치합니다. - 미등록 컬렉션은 자동으로 무시:
gov_faq_anthropic
미등록 상태여도 경고만 발생할 뿐 데모는 작동합니다 -
하나도 일치하지 않는 경우에는 제한을 적용하지 않음 (전멸 시에는 안전한 방향으로 폴백(Fallback) 및 경고 로그)
업종에 따라 설계 판단이 달라지는 지점은 "잠정적 대안을 보유할 것인가"입니다.
| 구분 | gov | saas | ec |
|---|---|---|---|
| 잠정적 대안 | 있음 (wikipedia_ja) | 없음 | 없음 |
| 이유 | 제도·일반 지식은 백과사전으로도 올바르게 답변 가능 | 제품 사양은 백과사전으로 올바르게 답변할 수 없음 | 반품 규정·배송비는 "자사의 규정"이므로 일반 지식으로 답변해서는 안 됨 |
EC의 "반품 규정을 타사 정책이나 Web의 일반론으로 답변해 버리는" 오류는, 스코프(Scope)를 한정함으로써 구조적으로 방지할 수 있습니다. 이는 업무 요구사항이 그대로 아키텍처 제약 사항이 되는 좋은 사례입니다.
prompt_addendum
5.3 업무 방침의 주입 — prompt_addendum
은 config.llm.prompt_addendum을 경유하여, ReasoningTool._build_prompt()의 시스템 지시(System Instruction) 직후에 "### 【업무 방침 (준수)】"로서 주입됩니다. ② Execute의 reasoning과 ⑤ Web 폴백(Fallback)의 reasoning 양쪽 모두에 영향을 미친다는 점이 포인트이며, Web을 경유하더라도 업종 특유의 말투나 금칙 사항이 무너지지 않습니다.
예를 들어 gov의 "단정을 피함 / 개인정보를 묻지 않음"은 require_identity=False(개인정보를 수집하지 않는 방침)와 일체화되어 설계되어 있습니다. 프로필의 각 항목은 독립적인 것이 아니라, 업종의 사상에 따라 연동되어 있습니다.
6. 판정 로직 ① 2단계 판정 — "환불 정책을 알려줘"와 "환불해 줘"를 구분하기
제2장의 "실패 2"로 돌아가겠습니다. 에스컬레이션(Escalation) 용어나 액션(Action) 용어는 FAQ 질문에도 흔히 나타납니다.
- gov: "감면 제도의 개요를 알려줘" (FAQ)와 "감면을 개별적으로 판단해 줘" (의뢰)
- saas: "과금 플랜의 차이를 알려줘" (FAQ)와 "과금이 이중으로 되어 있습니다" (장애 보고)
- ec: "반품 규정을 알려줘" (FAQ)와 "반품하고 싶어" (의뢰)
키워드 일치만으로 판정하면, FAQ 질문이 발생할 때마다 잘못된 에스컬레이션이나 잘못된 티켓 생성(Issue creation)이 발생합니다. 그래서 판정을 2단계로 나누었습니다.
- 제1단계 (후보 검출)
_match_keyword(): 키워드의 부분 일치. 일치하지 않으면 여기서 종료되며, LLM은 호출되지 않습니다 (추가 비용 제로). - 제2단계 (의도 분류)
create_intent_classifier(): 일치했을 때만 경량 LLM (claude-haiku-4-5-20251001)을 사용하여 문의를question(FAQ 질문) /request(실행 의뢰) /incident(장애·피해 보고) 중 하나로 분류합니다 (동일 쿼리는 메모이제이션(Memoization)하여 에스컬레이션 판정과action_map판정에서 공유).
판정 규칙 (_should_force_escalate / _decide_action):
| 제1단계 | 제2단계 (의도) | 결과 |
|---|---|---|
| 불일치 | (호출되지 않음) | 통상 플로우 |
| 일치 | question | 오작동 억제 — 에스컬레이션 하지 않음 / 티켓 생성 하지 않음 |
| 일치 | request / incident | 강제 에스컬레이션 / 티켓 생성 |
| 일치 | None (분류 실패) | 안전한 방향 — 기존 방식대로 에스컬레이션 / 티켓 생성 |
설계의 핵심은 두 가지입니다. 첫째, 분류에 실패하면 안전한 방향(사람에게)으로 넘기는 것입니다. LLM 판정은 확률적이기 때문에, 실패 시의 디폴트를 안전한 쪽으로 고정해 두면 최악의 경우에도 "사람에게 너무 많이 연결될" 뿐입니다. 둘째, 비용 설계입니다. 제2단계가 실행되는 것은 키워드가 일치할 때뿐이므로, 대부분의 문의에서는 판정 비용이 제로이며, 일치하더라도 Haiku 1회 호출로 충분합니다.
업종마다 다른 점은 "무엇과 무엇이 충돌하는가"입니다
판정 규칙 자체는 3개 업종 공통이며, 다른 점은 충돌하는 어휘의 성질입니다. 이 부분이 기술적으로 가장 흥미로운 대목입니다.
| gov | saas | ec | |
|---|---|---|---|
| 충돌의 성질 | |||
| 제도명에 에스컬레이션(Escalation) 어휘가 포함됨 (감면 제도·불복 심사 제도) | FAQ 어휘와 에스컬레이션 어휘가 동일 (과금·장애는 FAQ의 주제 그 자체) | FAQ 어휘와 액션(Action) 어휘가 동일 (반품·해지은 FAQ의 주제 그 자체) | |
| 억제하는 오작동 | |||
| 오·강제 에스컬레이션 | 오·강제 에스컬레이션 | 오·강제 에스컬레이션 + 오기표 | |
3개 업종의 실례를 정리하면 다음과 같습니다.
| 문의 | 업종 | 의도 | 결과 |
|---|---|---|---|
| 「감면을 개별적으로 판단해 주길 원한다」 | gov | request | 강제 에스컬레이션 (Web 검색도 스킵) |
| ... |
7. 판정 로직 ② 정보 없음 감지 (④') — 「정직한 '찾을 수 없습니다'」를 사람에게 넘기기
또 다른 난관은 2단계 판정의 반대편에서 발생했습니다. 에이전트가 정직하게 "찾을 수 없습니다"라고 대답할수록, 시스템은 그것을 "답변 성공"으로 오인하는 문제입니다.
예를 들어 EC에서 "이 상품의 입고 예정일은 언제인가요?"라는 질문을 받았을 때, 에이전트는 Web의 일반 정보로부터 "입고 예정일은 확인할 수 없었습니다. 상품 페이지에서 확인해 주세요"라는 정중한 답변을 만듭니다. 이 답변은 출처가 있고 지지율(Support score)도 붙기 때문에, 답변 게이트를 answer로 통과해 버립니다. 하지만 업무 관점에서는 이것을 유인 대응(사람)으로 넘겨야 하는 케이스입니다.
이 문제에 대한 대책은 3번의 재작업을 거쳤습니다.
대책 1: 정형구(定型句) 탐지 + 실질 답변 판정. "찾을 수 없습니다", "확인할 수 없습니다" 등의 정형구를 후보로 탐지하고, 일치할 때만 경량 LLM을 사용하여 "이 답변이 질문에 실질적으로 답하고 있는가 (answered / no_info)"를 판정하는 게이트(④')를 추가했습니다. 2단계 판정과 동일한 "후보 탐지 → LLM 판정" 구조를 재사용한 것입니다.
대책 2: 판정이 너무 엄격함 (실패와 시정). ④'를 도입하자 반대의 오작동이 발생했습니다. "저희 회사 고유의 규정은 찾을 수 없었으나, 일반적인 내용은 ~"와 같은 주의 사항이 포함된 실질적 답변까지 no_info로 판정되어, 답변 가능한 질문이 사람에게 넘어가 버린 것입니다. 판정 기준을 구체화하고, few-shot 판정 예시를 프롬프트에 추가하여 시정했습니다. 한때 KPI가 악화되었다가 회복되었으며, 이는 "안전장치는 설치하는 것으로 끝나는 것이 아니라, 그 자체의 오작동도 측정하고 고쳐나가야 한다"는 교훈이 되었습니다.
대책 3: 출처가 Web뿐이라면 판정을 필수화 (force_judge). 그럼에도 불구하고 놓치는 부분이 남았습니다. 정형구를 포함하지 않는 실질적 답변 스타일의 문구(예: 세제 개편의 '전망'을 검토 단계의 정보로 소개하는 답변)입니다. 그래서 "출처가 Web뿐 = 사내 근거 제로인 답변은, 정형구가 없더라도 반드시 ④' 판정을 실시한다"를 추가했습니다.
이때 판정 기준으로 언어화한 것이 다음의 2가지이며, 이것이 최종적으로 효과를 발휘했습니다.
- "질문된 사항 그 자체"와 "그것을 어디서 확인할 수 있는지에 대한 안내"를 구분한다. 안내만 있는 답변은 아무리 정중하더라도
no_info. - 미래의 예측을 묻는 질문에 확정 정보가 아닌 요청·검토 단계의 정보로 답하는 경우도
no_info.
반면, 일반 지식 질문에 공적 정보를 근거로 정의·특징을 설명하는 답변(예: "행정 불복 심사 제도란 어떤 제도인가요?")은 answered로서 보호하는 예시도 병기하여 오작동의 재발을 방지하고 있습니다.
8. 평가 — KPI 하네스(Harness)와 「의도적인 빈틈」
"안전하게 분류됩니다"라는 주장은 측정하지 않으면 말할 수 없습니다. 기대 라벨(Expected label)이 포함된 테스트 질문(gov 7 / saas 8 / ec 9 케이스)을 흘려보내고, KPI를 자동 측정하는 평가 하네스를 동봉했습니다.
테스트 질문은 5개 카테고리로, 각 분기를 하나씩 검증합니다.
| 카테고리 | 검증 내용 | 기대값 |
|---|---|---|
| in-scope | 나리지(Knowledge) 내의 FAQ에 답할 수 있는가 | answer |
| ... | keyword-trap | 에스컬레이션 어휘·액션 어휘를 포함한 질문에서 오작동하지 않는가 |
측정 메트릭은 10종(eval/vertical/metrics.py)이며, 업종마다 "가장 중시하는 지표"가 다릅니다.
| 메트릭 (Metrics) | 의미 | 특히 중시하는 업종 |
|---|---|---|
decision_accuracy | answer/escalate 분기 일치율 | 전 업종 |
false_escalate_rate | FAQ를 실수로 사람에게 넘긴 비율 | gov |
forced_escalate_misfire_rate | trap 오발화율 | saas |
escalate_recall | 넘겨야 할 것을 넘긴 비율 | saas |
citation_rate / ungrounded_answer_rate | 출처 부여율 / 근거 없는 답변율 | gov |
action_accuracy | 티켓 생성(起票) 필요 여부의 정확성 | ec |
identity_check_rate | 본인 확인 준수율 | ec |
mean_latency_ms | 평균 레이턴시 (Latency) | 전 업종 |
의도적인 「구멍」 설계
평가용 지식 (합성 Q&A)를 만들 때, 한 가지 공을 들였습니다. out-of-scope 질문(입고 예정일, 다음 분기 매출 전망, 세제 개편 예측)에 대응하는 데이터를 일부러 등록하지 않는 것입니다. 모든 것을 커버해 버리면 「모를 때 사람에게 넘길 수 있는가」라는 분기를 영원히 검증할 수 없게 되기 때문입니다. 이 「구멍」이 향후 데이터 추가로 인해 메워지지 않도록, CI 테스트가 가드(Guard)하고 있습니다.
측정 이력 — 0.857~0.889에서 1.000으로
분기 일치율 (decision_accuracy)의 추이입니다 (모두 합성 테스트 케이스에서의 값).
| 시점 | ec | saas | gov | 주요 변화 |
|---|---|---|---|---|
| 베이스라인 | 0.889 | 0.875 | 0.857 | 전용 지식 미등록. keyword-trap 판정이 실행마다 흔들림 |
| ... | 1.000 (9/9) | 0.875 (7/8) | 1.000 (7/7) | out-of-scope 누락 (escalate_recall)이 ec 0.667→1.000, gov 0.500→1.000으로 회복 |
**SaaS의 남은 1건 (7/8)**도 원인을 특정했습니다. 「500 에러가 발생하는 결함을 보고하고 싶다」라는 질문에서 Web 검색이 타임아웃되어, 검색 0건 → 정보 없음 답변 → ④' 에스컬레이션(Escalate)으로 이어지는 연쇄 작용이었습니다 (기대값은 답변 + 티켓 생성). Web 검색 측에 재시도(Retry) 설정과 폴백(Fallback) 백엔드를 구현 완료했으며, 재측정 시 8/8 도달을 확인하는 단계입니다.
이 프로세스를 통해 실감한 것은, KPI 측정은 실패 패턴을 발견하는 장치라는 점입니다. 「out-of-scope × 동적 Web 검색」이라는 공통 패턴도, 「④' 판정이 너무 엄격하다」라는 안전장치 자체의 오작동도, 수치 저하로 먼저 나타났으며 로그를 추적함으로써 원인에 도달할 수 있었습니다.
9. 운영의 현실 — 비용과 레이턴시
PoC를 검토할 때 필요하게 되는 실측치도 기록하고 있습니다.
- 1 케이스 (1회 문의 평가 실행) ≈ 9엔. 내역은 LLM 호출 약 7
10회 (답변 생성 · 단계별 확신도 평가 · 출처 검증 · 의도 분류 · 정보 없음 판정 등) - 가장 큰 비용 항목은 단계별 확신도 평가(약 34%)였기에, 이 처리를 경량 모델 (Haiku)로 전환하여 약 −23%/케이스로 절감 - 판정 품질에 대한 영향은 측정상 없었습니다 - 레이턴시는 1 케이스 6575초 → 38~41초로 단축 (동일한 Haiku 전환 효과) - 반복 검증 비용을 억제하는 옵션:--limit N(앞부분 N건의 스모크 테스트) ·--no-web(Web 폴백 무効) ·--cases(실패 케이스만 재실행)
10. 솔직한 현재 위치와 향후 계획
잘된 수치만 나열하면 실태를 오해할 수 있으므로, 현재 위치를 솔직하게 적습니다.
강점 (실질적인 차별화): 에스컬레이션 기준 · 액션 · 본인 확인. 같은 「반품하고 싶다」라도, EC에서는 「본인 확인 → 사람의 승인 → 티켓 생성」, 지자체라면 「유인 창구로 안내」와 같이, 업무 설계의 차이를 코드가 실제로 분기하고 있습니다. 본인 확인은 대장 대조를 포함하며, 확인되지 않으면 실행하지 않고 사람에게 인계합니다 (--no-dry-run 시 SUPPORT_IDENTITY_FILE의 고객 대장 CSV와 order_id / email을 대조, 실행은 SUPPORT_ACTION_WEBHOOK_URL로 수행).
설정 시 Webhook 연동).
미흡한 부분 (아직 프레임워크 단계): 지식 (Knowledge)은 평가용 합성 데이터 (각 업종별 20건) 단계입니다. 실운용 지식 취득 스크립트 (gov = e-Gov 법령 API, SaaS = OSS 공식 문서)는 정비되어 있으나, 실제 데이터로의 계측은 이제부터 시작입니다. 임계값 (Threshold)과 업무 방침문도 「특화」라기보다는 업종별 튜닝 (Tuning)을 위한 장소이며, 업계 용어 사전이나 제도 개정에 대한 추종은 미구현 상태입니다.
향후에는 실운용 데이터의 투입과 재계측, 그리고 4번째 업종의 추가 (프로필 1개와 지식 등록만으로 가능한지에 대한 검증)를 진행할 예정입니다.
11. 실행 방법 (Quick Start)
# 1. 환경 변수 (.env)
# ANTHROPIC_API_KEY=... # LLM (Claude)
# GOOGLE_API_KEY=... # Embedding (Gemini)
...
실제 데이터를 넣는 경우에는 업종별 문서 (docs/vertical_*.md)의 「투입 절차」에 e-Gov 법령 API / OSS docs / 자사 CSV로부터의 등록 명령어를 기재해 두었습니다.
12. 링크 모음
- Claude API 버전 (본 기사의 구현): https://github.com/nakashima2toshio/anthropic_grace_agent_v2
- 로컬 LLM 버전 (Ollama · 온프레미스용): https://github.com/nakashima2toshio/ollama_grace_agent_v2
- 상세 문서 (리포지토리 내)
- docs/vertical_comparison.md — 3개 업종의 병렬 비교 (8개 관점)
- docs/vertical_gov.md / vertical_saas.md / vertical_ec.md — 업종별 특화 부분
- docs/agent_support_example.md — 본체의 사양 (IPO 형식)
- grace/doc/agent_support_verticals.md — 업계 특화 설계서 (개선 이력 · KPI 계측 이력 포함)
일본어 RAG · 사내 지식 검색 · 자율 에이전트의 PoC (Proof of Concept)부터 온프레미스 본운용화까지 도와드리고 있습니다. 「클라우드에 올릴 수 없는 데이터로 테스트하고 싶다」거나 「PoC 단계에서 멈춰 있다」는 분들은 GitHub 또는 X의 DM으로 문의해 주세요.
Discussion

AI 자동 생성 콘텐츠
본 콘텐츠는 Zenn AI의 원문을 AI가 자동으로 요약·번역·분석한 것입니다. 원 저작권은 원저작자에게 있으며, 정확한 내용은 반드시 원문을 확인해 주세요.
원문 바로가기