Spaces:
Sleeping
title: Insurance Chatbot
emoji: ๐ฅ
colorFrom: indigo
colorTo: purple
sdk: docker
app_port: 7860
pinned: false
AI TMR Assistant โ Tool Routing ๊ณ ๋ํ
Intelligent Tool Routing์ผ๋ก ์ ํ๋๋ฅผ ๊ฐ์ ํ๊ณ , Scalable Tool Architecture๋ก ์ด์ ํจ์จ๊ณผ ํ์ฅ์ฑ์ ๋์์ ํ๋ณดํจ
1. ๋ฌธ์
12๊ฐ ๋ณดํ ์ํ ร 9๊ฐ ๊ธฐ๋ฅ(์กฐํยท์ฐ์ถยท์ฌ์ฌยท๋ณด์ฅยท์ฒญ๊ตฌ ๋ฑ) = 54๊ฐ ๋๊ตฌ. ๋๊ตฌ๊ฐ ๋ง์์ง๋ฉด์ ์ธ ๊ฐ์ง ๋ฌธ์ ๊ฐ ์๊น.
| ๋ฌธ์ | ์์ธ | ์ํฅ |
|---|---|---|
| ์คํธ์ถ | ์ ์ฌ ๋๊ตฌ ํผ๋ (premium_estimate โ plan_options) | ์๋ชป๋ ๋ต๋ณ |
| ๋น์ฉ ์ฆ๊ฐ | ๋งค ์์ฒญ๋ง๋ค 54๊ฐ ์คํค๋ง๊ฐ LLM ์ปจํ ์คํธ์ ํฌํจ๋จ | ํ ํฐ ๋ญ๋น |
| ์ง์ฐ ์ฆ๊ฐ | ์ปจํ ์คํธ ๊ธธ์ด์ ๋น๋กํ์ฌ ์๋ต ์๊ฐ์ด ์์นํจ | UX ์ ํ |
๋๊ตฌ 10๊ฐ๋ฅผ ๋์ผ๋ฉด ์ ํ๋๊ฐ ๋จ์ด์ง๊ณ , 37๊ฐ ๊ธฐ์ค ~6,200 ํ ํฐ์ด ์๋น๋จ (์ฐธ๊ณ ). "์ ๋ถ ๋๊ธฐ์ง ๋ง๊ณ ํ์ํ ๊ฒ๋ง ๊ฒ์ํด์ ๋๊ธฐ์" โ ์ด๊ฒ์ด RAG-MCP ํจํด์ ํต์ฌ์ (์ฐธ๊ณ ).
2. ์ค๊ณ โ ๋ ์ถ์ ์ ๋ต
์ด ํ๋ก์ ํธ๋ ๋ ๊ฐ์ ์ถ์ผ๋ก ๋ฌธ์ ๋ฅผ ํด๊ฒฐํจ.
| ์ ๋ต ์ถ | ํต์ฌ | ๋ชฉํ |
|---|---|---|
| Intelligent Tool Routing | ์คํธ์ถ์ ์ค์ด๊ณ ์ ํํ ํธ์ถ๋ง ๋จ๊น | ์ ํ๋ยท๋น์ฉยท์ง์ฐ ๊ฐ์ |
| Scalable Tool Architecture | ์ ๊ท ๋๊ตฌ ์ถ๊ฐ๊ฐ ์ด์ ๋ถ๋ด์ด ๋์ง ์๋๋ก ์๋ํ | ํ์ฅ์ฑยท์ด์ ํจ์จ |
์๋๋ ๋ ์ถ์ด ์ค์ ์์คํ ์์ ์ด๋ป๊ฒ ์ฐ๊ฒฐ๋๋์ง๋ฅผ ๋ํ๋.
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ Intelligent Tool Routing โ
โ โ
โ ์ฌ์ฉ์ ์ง๋ฌธ โ
โ โผ โ
โ [Guardrail] โโโ ๋น๋ณดํ ์ง๋ฌธ ์ฐจ๋จ โโโ ๊ฑฐ์ ์๋ต โ
โ โ (ํต๊ณผ) โ
โ โผ โ
โ [Tool Card ๋งค์นญ] โโโ ChromaDB ๋ฉํฐ๋ฒกํฐ โ Top-5 ์ถ์ถ โ
โ โผ โ
โ [LLM Tool Call] โโโ ํ๋ณด ์ค ์ต์ข
์ ํ โ ์คํ โ
โ โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โฒ
โ Vector Index ์ฐธ์กฐ
โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
โ Scalable Tool Architecture โ
โ โ
โ ์ Tool ์ถ๊ฐ โ Tool Card ์์ฑ โ ์๋ฒ ๋ฉ ์๋ ์์ฑ โ
โ โ Vector Index ์๋ ๊ฐฑ์ โ
โ โ
โ Validation: Recall@k ํ๊ฐ โ ์์น ๊ธฐ๋ฐ ์์ฌ๊ฒฐ์ ๊ทผ๊ฑฐ โ
โโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโโ
3. ์ถ โ โ Intelligent Tool Routing
3-1. 3๋จ๊ณ ํํฐ๋ง์ผ๋ก 54๊ฐ๋ฅผ 5๊ฐ๋ก ์ค์
| ๋จ๊ณ | ๋ชจ๋ | ๊ธฐ๋ฅ | ์๋ |
|---|---|---|---|
| Guardrail | ์ ๊ท์(L1) + ์๋ฒ ๋ฉ(L2) | ํ์ฅยท๋น๋ณดํ ์ง๋ฌธ ์ฌ์ ์ฐจ๋จ | <5ms |
| Tool Search | ChromaDB ๋ฉํฐ๋ฒกํฐ | 54๊ฐ โ Top-K ํ๋ณด ์ถ์ถ | ~10ms |
| LLM Selection | bind_tools() | ํ๋ณด ์ค ์ต์ข ๋๊ตฌ ์ ํยทํธ์ถ | 1~5s |
Guardrail์ด ๋จผ์ ๋์ํ๋ฏ๋ก "์ค๋ ๋ ์จ ์ด๋?" ๊ฐ์ ์ง๋ฌธ์ ๋ฒกํฐ ๊ฒ์์ด๋ LLM ํธ์ถ ์์ด ์ฆ์ ์ฐจ๋จ๋จ.
3-2. Tool Card๋ก ๊ฒ์ ์ ํ๋๋ฅผ ๋์
LLM ๋๊ตฌ description์ ๋ณดํต ํ๋ ์ค์ด๋ผ, ์ ์ฌ ๋๊ตฌ๋ผ๋ฆฌ ๋ฒกํฐ๊ฐ ๊ฑฐ์ ๊ฐ์์ ธ์ ๊ตฌ๋ถ์ด ์ด๋ ค์. ์ด๋ฅผ ํด๊ฒฐํ๊ธฐ ์ํด ๋๊ตฌ๋ง๋ค ToolCard๋ฅผ ์์ฑํ์ฌ ์๋ฒ ๋ฉ ํ๋ฉด์ ํ์ฅํจ.
ToolCard(
name="premium_estimate",
purpose="๋์ดยท์ฑ๋ณ์ ์
๋ ฅํด ํน์ ์ํ์ ์์ ์ ๋ณดํ๋ฃ๋ฅผ ์ฐ์ถํ๋ค.",
when_to_use=("๋ณดํ๋ฃ ์ผ๋ง์ผ?", "40์ธ ๋จ์ฑ ๋ณดํ๋ฃ ๊ณ์ฐํด์ค"),
when_not_to_use=("๋ฉ์
ํ๋์ด ๊ถ๊ธํ๋ค โ plan_options ์ฌ์ฉ",),
tags=("๋ณดํ๋ฃ", "์ฐ์ถ"),
)
| ํ๋ | ์๋ฒ ๋ฉ ํฌํจ | ์ญํ |
|---|---|---|
purpose |
O | ๋๊ตฌ์ ํต์ฌ ๊ธฐ๋ฅ์ ํ ๋ฌธ์ฅ์ผ๋ก ์ค๋ช |
when_to_use |
O | ์ค์ ์ฌ์ฉ์ ๋ฐํ ์์ โ ๊ฒ์ ํ๋ฉด ํ์ฅ |
tags |
O | ๋๋ฉ์ธ ํค์๋ โ ํด๋ฌ์คํฐ๋ง ๋ณด์กฐ |
when_not_to_use |
X | ํผ๋ ๊ฐ๋ฅํ ๋๊ตฌ ์๋ด โ LLM ์ต์ข ์ ํ ์์๋ง ์ฌ์ฉ |
when_not_to_use๋ฅผ ์๋ฒ ๋ฉ์์ ์ ์ธํ๋ ์ด์ : ํ ๋๊ตฌ ์ด๋ฆ("premium_estimate ์ฌ์ฉ")์ด ํฌํจ๋๋ฉด ๋ฒกํฐ๊ฐ ์ค์ผ๋จ.
Tool-DE (Lu et al., 2025) ablation์์๋ negative example ํฌํจ ์ ์ฑ๋ฅ์ด ์ ํ๋จ.
3-3. Multi-Vector ์ธ๋ฑ์ฑ
๊ฐ ToolCard ํ๋๋ฅผ ๋ณ๋ ๋ฌธ์๋ก ChromaDB์ ์ธ๋ฑ์ฑํ๊ณ , ๊ฒ์ ์ tool๋ณ max score๋ก ์ง๊ณํจ. ๋จ์ผ ๋ฒกํฐ๋ก ํฉ์น๋ฉด ์ฌ๋ฌ ์์์ ํ๊ท ์ผ๋ก ํฌ์๋์ง๋ง, ์ด ๋ฐฉ์์ ColBERT ๋ฑ multi-vector ๋ชจ๋ธ๊ณผ ๋์ผํ ์๋ฆฌ๋ก ํฌ์ ์์ด ์ ํํ ๋งค์นญ์ด ๊ฐ๋ฅํจ (Pinecone).
4. ์ถ โก โ Scalable Tool Architecture
4-1. ๋๊ตฌ ์ถ๊ฐ๊ฐ ์ด์ ๋ถ๋ด์ด ๋์ง ์๋๋ก
์ Tool ์ถ๊ฐ โ Tool Card ์์ฑ โ ์๋ฒ ๋ฉ ์๋ ์์ฑ โ ์ฆ์ ๊ฒ์ ๋์์ ํฌํจ
| ๋ฐฉ์ | ์ ์ฐจ | ์๋ฒ ์ฌ์์ |
|---|---|---|
| ์ ์ ๋ฑ๋ก | Tool ํจ์ + ToolCard โ ์๋ฒ ์ฌ์์ | ํ์ |
| ๋ฐํ์ ํซ๋ฆฌ๋ก๋ | Tool ํจ์ + API ํธ์ถ | ๋ถํ์ |
ToolRegistry๊ฐ ๋์ ๊ด๋ฆฌํ๊ณ , ๋ณ๊ฒฝ ์ ChromaDB ์ฌ์ธ๋ฑ์ฑ์ ์๋ ํธ๋ฆฌ๊ฑฐํจ.
4-2. ์ฝ๋ ๋ณ๊ฒฝ ์์ด ์ด์ ์ค ํ๋
Admin Dashboard(/admin/tools)์์ ToolCard๋ฅผ ์์ ํ๋ฉด ์ฆ์ ์ฑ๋ด์ ๋ฐ์๋จ.
๋ฐฐ์น Recall ํ๊ฐ์ LLM ๋ถ์์ ๋ด์ฅํ์ฌ, ์์ ์ ํ ์ฑ๋ฅ ์ฐจ์ด๋ฅผ ๋ฐ๋ก ํ์ธํ ์ ์์.
Admin UI์์ when_to_use ๋ฌธ์ฅ ์์
โ [์ ์ฅ & ๋ฐ์] ํด๋ฆญ
โ ๋ฉ๋ชจ๋ฆฌ REGISTRY ์
๋ฐ์ดํธ + ChromaDB ์ฌ์ธ๋ฑ์ฑ
โก data/toolcard_overrides.json ์ ์ฅ (์๋ฒ ์ฌ์์ ํ์๋ ์ ์ง)
โข ๋ฒ์ ์ด๋ ฅ ๊ธฐ๋ก โ ๋ฌธ์ ์ ๋กค๋ฐฑ ๊ฐ๋ฅ
4-3. Validation โ ๊ฐ์ด ์๋ ์์น๋ก ํ๋จ
scripts/eval_tool_recall.py๋ก Recall@k, MRR, Hit@1์ ์ ๋ ์ธก์ ํจ.
Admin Dashboard ํต ํ
์คํธ ํญ์์๋ ๊ฐ๋ณ ๋๊ตฌ์ ๋ฐฐ์น Recall ํ๊ฐ์ LLM ์คํจ ๋ถ์์ ์ํํ ์ ์์.
python -m scripts.eval_tool_recall --compare # k=1,3,5,7,10 ๋น๊ตํ
python -m scripts.eval_tool_recall --verbose # ์คํ ์ฌ๋ก ์์ธ
5. ๊ฒฐ๊ณผ
79๊ฐ ํ ์คํธ ์ฟผ๋ฆฌ(tool-call 64๊ฐ + no-call 15๊ฐ) ํ๊ฐ ๊ฒฐ๊ณผ:
| ์งํ | k=1 | k=3 | k=5 (์ด์) | k=7 | k=10 |
|---|---|---|---|---|---|
| Recall@k | 96.9% | 100% | 100% | 100% | 100% |
| Hit@1 | 96.9% | โ | 96.9% | โ | 96.9% |
| MRR | 0.969 | 0.984 | 0.984 | โ | 0.984 |
| No-Call Acc | โ | โ | 80.0% | โ | 80.0% |
- k=1 ๋ฏธํ 2๊ฑด: ์ ์ฌ ๋๊ตฌ ๊ฒฝ๊ณ ์ฌ๋ก (coverage_detail โ benefit_amount, renewal_projection โ renewal_notice)
- k=3๋ถํฐ Recall 100% โ 64๊ฐ tool-call ์ฟผ๋ฆฌ๊ฐ ์ ๋ถ Top-3 ์์ ํฌํจ๋จ
- no-call ์คํ 3๊ฑด: ์ ์ฌ๋ 0.86~0.88๋ก ๊ฒฝ๊ณ์ ๊ฑธ๋ฆฌ์ง๋ง, Guardrail์์ ์ฌ์ ์ฐจ๋จ๋๋ฏ๋ก ์ค์ด์์์๋ Tool Search์ ๋๋ฌํ์ง ์์
54๊ฐ โ 5๊ฐ๋ก 90% ์ถ์ํด๋ Recall@5 = 100%, MRR = 0.98. ์ ํ๋๋ฅผ ์ ์งํ๋ฉด์ ๋น์ฉ๊ณผ ์ง์ฐ์ ๋์์ ์ค์.
5-1. ๋ฉํฐํด ์๋๋ฆฌ์ค ์คํ ๊ฒฐ๊ณผ
5๊ฐ TMR ์ค์ ์๋ด ์๋๋ฆฌ์ค๋ฅผ ๊ตฌ์ถํ์ฌ end-to-end ๊ฒ์ฆ์ ์ํํจ.
| # | ์๋๋ฆฌ์ค | ํด | ํต์ฌ ๊ฒ์ฆ ํฌ์ธํธ | ์ฌ์ฉ๋ ๋๊ตฌ |
|---|---|---|---|---|
| 1 | ๊ธฐ๊ฐ์ ๊ณ์ฝ์ ์ ์ง๋จ โ ์ฒญ๊ตฌ | 4 | ๊ณ์ฝ ์กฐํ(2๊ฑด ์ ์ง, ๊ณ์ฝ์ผยท๋ง๋ฃ์ผยท๊ฐฑ์ ์ผ) โ ์ง์ ์กฐํํ ์๋ณดํ ๊ธฐ์ค ์ฒญ๊ตฌ ์๋ด(๊ฐ์ ๋ถ๊ฐ ์๋) โ ์ฒญ๊ตฌ ํ์ ์๋ฅ โ ๊ธฐ๊ฐ์ ๊ธฐ๋ฐ ์ถ๊ฐ ๋ณด์ฅ ์ถ์ฒ | customer_contract_lookup, event_eligibility_check, claim_required_forms, product_search |
| 2 | ๊ธฐ๊ฐ์ ๊ณ์ฝ์ ์ถ๊ฐ ์ํ ์ค๊ณ | 4 | ๊ณ์ฝ ํ์ธ(55์ธยท์ฌ์ฑยท3๊ฑด ์ ์ง) โ ์น๋งค ๋ณด์ฅ ์ถ๊ฐ ์ ์ค๋ณต ์๋ ์ํ โ ์น๋งค๊ฐ๋ณ vs ์ค์์น๋งค 55์ธ ์ฌ์ฑ ๋ณดํ๋ฃ ๋น๊ต โ ๋ณด์ 3๊ฑด ํฉ์ฐ ์ ๋ณดํ๋ฃ(๋งฅ๋ฝ ์ฌ์ฉ) | customer_contract_lookup, product_search, premium_compare, premium_estimate |
| 3 | ํด์ง๋ ๋ณดํ ๋ถํ + ๋์ | 4 | ์ ์ง/ํด์ง ๊ตฌ๋ถ(ํด์ง์ผ ํ์) โ ๋ถํ ์กฐ๊ฑด(3๋ ยท์ฐ์ฒด๋ณดํ๋ฃ ๋ฑ) โ 60์ธ ์ฌ์ฑ ๋์ ์๋ณดํ โ ์ ์ง ์ค ์ข ์ ๋ณดํ ๋ณด์ฅ ๋ด์ฉ | customer_contract_lookup, underwriting_reinstatement_rule, product_search, coverage_summary |
| 4 | ๊ณ ์ํ ์ง์ + ์ ๋ณ๋ ฅ ์ฌ์ฌ | 4 | ๋ณตํฉ ์กฐ๊ฑด(์ง์ ยท๋ณ๋ ฅ) ์ธ์ โ ํ ์ฆ ์ง๊ตฐ ํ์ธ โ ์ฒซ๋ ๋ถํฐ์๋ณดํ ๋ณด์ฅ ์์ธ โ ๊ฐํธ์ฌ์ฌ ๊ฑด๊ฐ๋ณดํ | underwriting_precheck, underwriting_high_risk_job_check, coverage_detail, product_search |
| 5 | ์๋์ด ์ข ํฉ ์ค๊ณ | 4 | 70์ธ ์๋ฒ์ง(๋จ์ฑ) ์ฌ๋งยท์น์ ์ํ ์ถ์ฒ โ ๊ฑด๊ฐํด์ง๋์ข ์ ์ฐ๊ธ์ ํ โ ๋ ๋ ํ์ค๋ฒ์น์ 70์ธ ๊ฐ์ ยท๋ณด์ฅ โ ์ง์ ๋ ์ํ ํฉ์ฐ ๋ณดํ๋ฃ(70์ธ ๋จ์ฑ) | product_search, coverage_summary, premium_estimate |
๊ณ์ฝ์ ์ ๋ณด ์ฒ๋ฆฌ:
- ๊ณ์ฝ์ ์ด๋ฆ์ผ๋ก
customer_contract_lookupํธ์ถ โ ๊ณ์ฝ์IDยท์ฑ๋ณ(๋จ์ฑ/์ฌ์ฑ)ยท๋์ด + ๋ณด์ ๊ณ์ฝ(์ ์ง/ํด์ง) ์ฆ์ ํ์ธ - ๊ณ์ฝ ์ ๋ณด์ ๋ณดํ ์ฉ์ด ์ ์ฉ: ๊ณ์ฝ์ํ(์ ์งยทํด์งยท์คํจยท๋ง๊ธฐ), ๊ณ์ฝ์ผ, ๋ง๋ฃ์ผ, ํด์ง์ผ, ๊ฐฑ์ ์ผ
- ๋ฐํ ๋ฐ์ดํฐ์์ ์ ํ๋ฒํธ ๋ฑ PII๋ฅผ ์์ค ๋ ๋ฒจ์์ ํํฐ๋ง (
_safe_customer/_safe_contract) - ๊ธฐ๊ฐ์ ์ํ์์ ์ง๋ณ ์ง๋จ ์ โ ๊ฐ์ ๋ถ๊ฐ๊ฐ ์๋ ๋ณดํ๊ธ ์ฒญ๊ตฌ ์ ์ฐจ ์๋ด๋ก ์ ํ
- ๋ณด์ ๊ณ์ฝ ๊ธฐ๋ฐ ์ค๋ณต ๊ฐ์ ์ฌ๋ถ ํ์ธ ํ ์ถ๊ฐ ์ํ ์ถ์ฒ
- ๋ํ ๋ด๋ด ๊ณ์ฝ์ ๋งฅ๋ฝ ์ ์ง (๊ฐ์ ID/์ด๋ฆ์ ์ฌ์๊ตฌํ์ง ์์)
์ถ๋ ฅ ํ์ง ๊ด๋ฆฌ:
- ์ํ์ฝ๋(B00...) ์ถ๋ ฅ ๊ฐ๋๋ ์ผ์์ ์๋ ์ ๊ฑฐ
- ๋ด๋ถ ๋๊ตฌ๋ช (snake_case) ์ถ๋ ฅ ๊ฐ๋๋ ์ผ์์ ์๋ ์ ๊ฑฐ
- ๋ฉด์ฑ ๋ฌธ๊ตฌ ์ค๋ณต ๋ฐฉ์ง (LLM ์์ฑ๋ถ์ด ์์ผ๋ฉด ๊ฐ๋๋ ์ผ ์ถ๊ฐ ์๋ต)
- ์๋ต ์ต๋ 7์ค, ํต์ฌ ์ ๋ณด๋ง ๊ฐ๊ฒฐํ๊ฒ ์ ๋ฌ
ํ์ ๋จ๋ต ์ฒ๋ฆฌ:
- "์๋ฒ์ง" โ ๋จ์ฑ์ผ๋ก ์ธ์, "์ด๋จธ๋" โ ์ฌ์ฑ์ผ๋ก ์ธ์
- query_rewriter๊ฐ 1~3๊ธ์ ๋จ๋ต์ ์ด์ ๋งฅ๋ฝ์ ํฉ์ณ์ ์์ ํ ์ง๋ฌธ์ผ๋ก ์ฌ์์ฑ
5-2. ์๋๋ฆฌ์ค ํด๋ณ ๊ฒ์ฆ ํฌ์ธํธ (๋ฉํฐํด ํ์ง ์ฒดํฌ)
๋ฉํฐํด ์๋๋ฆฌ์ค ์คํ ์ ๋งค ํด๋ง๋ค ์๋๋ฅผ ํ์ธํ๋ฉด, ๋งฅ๋ฝ ์ดํดยท์ง์ ์๋ต ๊ธฐ๋ฐ ๋ต๋ณ ์ฌ๋ถ๋ฅผ ๊ฒ์ฆํ ์ ์์.
| ์๋๋ฆฌ์ค | ํด | ์ฌ์ฉ์ ์ง๋ฌธ | ์ง์ ๋งฅ๋ฝ | ์ฑ๋ด์ด ํด์ผ ํ ์ผ | ๊ฒ์ฆ ํฌ์ธํธ |
|---|---|---|---|---|---|
| 1. ๊น๋ฏผ์ ์ ์ง๋จ | 1 | ๊ณ์ฝ์ ๊น๋ฏผ์๋ ๊ณ์ฝ ์กฐํํด์ค | ์์ | customer_contract_lookup(์ด๋ฆ=๊น๋ฏผ์) | ๊ณ์ฝ 2๊ฑด ์ ์ง(์+์น์), ๊ณ์ฝ์ผยท๋ง๋ฃ์ผ ํ๊ธฐ |
| 1 | 2 | ๊ฐ์์ ์ ์ง๋จ๋ฐ์๋๋ฐ ๊ฐ์ ์ค์ธ ์๋ณดํ์ผ๋ก ๋ณดํ๊ธ ์ฒญ๊ตฌ ๊ฐ๋ฅํด? | ๊น๋ฏผ์ 2๊ฑด ์ ์ง(์น์+์) | event_eligibility_check โ ์ฒญ๊ตฌ ์๋ด(๊ฐ์ ๋ถ๊ฐ ์๋) | ๊ธฐ๊ฐ์ ์๋ณดํ ๊ธฐ์ค ์ฒญ๊ตฌ ๊ฐ๋ฅ ์ฌ๋ถยท์ ์ฐจ ์๋ด |
| 1 | 3 | ์ฒญ๊ตฌ ์ ์ฐจ๋ ํ์ํ ์๋ฅ ์๋ ค์ค | ์ง์ ์ ์ฒญ๊ตฌ ๊ฐ๋ฅ ์๋ดํจ | claim_guide | ์ฒญ๊ตฌ์๋ฅยท๋ฐฉ๋ฒยท์ฒ๋ฆฌ๊ธฐ๊ฐ, ์ง์ ๋ํ ๋งฅ๋ฝ ์ ์ง |
| 1 | 4 | ์ง๊ธ ๊ฐ์ ํ ์ํ ์ธ์ ์ถ๊ฐ๋ก ๋ฃ์ผ๋ฉด ์ข์ ๋ณด์ฅ ์์ด? | ๊น๋ฏผ์ ๋ณด์ (์น์ยท์) | ์ค๋ณต ํ์ธ ํ ์ถ๊ฐ ๋ณด์ฅ ์ถ์ฒ | ๊ธฐ๊ฐ์ ๊ธฐ๋ฐ ์ค๋ณต ์๋ ์ํ๋ง ์ถ์ฒ |
| 2. ์ค์ง์ ์ถ๊ฐ ์ค๊ณ | 1 | ๊ณ์ฝ์ ์ค์ง์๋ ๊ณ์ฝ ์กฐํํด์ค | ์์ | customer_contract_lookup(์ด๋ฆ=์ค์ง์) | 55์ธ ์ฌ์ฑ, 3๊ฑด ์ ์ง, ๊ณ์ฝ์ผยท๋ง๋ฃ์ผยท๊ฐฑ์ ์ผ |
| 2 | 2 | ์น๋งค ๋ณด์ฅ์ ์ถ๊ฐํ๊ณ ์ถ์๋ฐ, ์ง๊ธ ๊ฐ์ง ์ํ์ด๋ ์ ๊ฒน์น๋ ์น๋งค๋ณดํ ์์ด? | ์ค์ง์ 3๊ฑด(๊ฐํธ๊ฑด๊ฐยท์น์ยท์ข ์ ) | product_search(์น๋งค) + ์ค๋ณต ์ฌ๋ถ ํ๋จ | ์น๋งค ์ํ 2์ข , ๊ธฐ๊ฐ์ ๊ณผ ๊ฒน์น์ง ์๋ ๊ฒ๋ง |
| 2 | 3 | ์น๋งค๊ฐ๋ณ๋ณดํ์ด๋ ์ค์์น๋งค๋ณดํ ์ฐจ์ด๊ฐ ๋ญ์ผ? 55์ธ ์ฌ์ฑ ๊ธฐ์ค ๋ณดํ๋ฃ๋ ๋น๊ตํด์ค | ์ค์ง์ 55์ธ ์ฌ์ฑ | coverage_summary + premium_estimate | 55์ธ ์ฌ์ฑ ๊ธฐ์ค ๋น๊ต, ์ง์ ํด ๋์ดยท์ฑ๋ณ ์ฌ์ฌ์ฉ |
| 2 | 4 | ์ง๊ธ ์ ์ง ์ค์ธ ์ธ ๊ณ์ฝ ํฉ์ฐ ์ ๋ณดํ๋ฃ๋ ์ผ๋ง์ฏค ๋ผ? | ์ค์ง์ 55์ธ ์ฌ์ฑ, 3๊ฑด | premium_estimate(55, F) 3๊ฑด ๊ฐ๊ฐ ํธ์ถ ํ ํฉ์ฐ | "์กฐํํ ์ ์์ต๋๋ค" ๊ธ์ง. 3๊ฑด ํฉ๊ณ ์ ์ |
| 3. ์ต์์ง ๋ถํ | 1 | ๊ณ์ฝ์ ์ต์์ง๋ ๊ณ์ฝ ํํฉ ์๋ ค์ค | ์์ | customer_contract_lookup(์ด๋ฆ=์ต์์ง) | ์ ์ง 1๊ฑด(์ข ์ ) + ํด์ง 1๊ฑด(์), ํด์ง์ผ ํ๊ธฐ |
| 3 | 2 | ํด์ง๋ ์๋ณดํ ๋ค์ ๋ถํํ ์ ์์ด? ์กฐ๊ฑด์ด ๋ญ์ผ? | ์ต์์ง ํด์ง๋ ์๋ณดํ(ํด์ง์ผ 2023-12-31) | underwriting_reinstatement_rule | ๋ถํ ๊ธฐํ(ํด์ง์ผ+3๋ ), ์ฐ์ฒด๋ณดํ๋ฃยท๋ฉด์ฑ ์ฌ์ ์ฉ ๋ฑ |
| 3 | 3 | ๋ถํ์ด ์ด๋ ค์ฐ๋ฉด 60์ธ ์ฌ์ฑ์ด ์๋ก ๊ฐ์ ํ ์ ์๋ ์๋ณดํ ์์ด? | ์ต์์ง 60์ธ ์ฌ์ฑ | product_search(์) + ๊ฐ์ ์กฐ๊ฑด | 60์ธ ์ฌ์ฑ ๊ธฐ์ค, ์ง์ ๋งฅ๋ฝ ๋์ดยท์ฑ๋ณ ์ฌ์ฉ |
| 3 | 4 | ์ ์ง ์ค์ธ ๊ฐํธ๊ณ ์ง์ข ์ ๋ณดํ ๋ณด์ฅ ๋ด์ฉ ์์ธํ ์๋ ค์ค | ์ต์์ง ์ ์ง 1๊ฑด ์ข ์ | coverage_detail | ์ง์ ์กฐํํ ์ข ์ ๋ณดํ ๋ณด์ฅ ์์ธ(์ฌ๋ง๋ณดํ๊ธยท๊ฐ์กยทํด์ฝํ๊ธ๊ธ) |
| 4. ํ์๊ธฐ์ฌ+๊ณ ํ์ | 1 | 48์ธ ๋จ์ฑ์ธ๋ฐ ํ์๊ธฐ์ฌ์ผ. ๊ณ ํ์ ์ฝ ๋ณต์ฉ ์ค์ด๊ณ ์๋ณดํ ๊ฐ์ ํ๊ณ ์ถ๋ | ์์ | ์ง์ ยท์ ๋ณ๋ ฅ ํ์ | ๋ณตํฉ ์ง๋ฌธ ์ธ์, ๋จ๊ณ๋ณ ๋ต๋ณ ๊ฐ๋ฅ ์๋ด |
| 4 | 2 | ํ์๊ธฐ์ฌ๋ฉด ์ง์ ์ํ๋ฑ๊ธ ๋๋ฌธ์ ๋ณดํ๋ฃ๊ฐ ๋ ๋น์ธ์ง๊ฑฐ๋ ๊ฑฐ์ ๋ ์ ์์ด? | 48์ธ ๋จ์ฑ, ํ์๊ธฐ์ฌ | underwriting_high_risk_job_check | ํ ์ฆ ์ง๊ตฐ ํ์ธ, ๋ณดํ๋ฃ ์ํฅ ์๋ด |
| 4 | 3 | ์ฒซ๋ ๋ถํฐ์๋ณดํ์ ๊ฐ์ ์กฐ๊ฑด์ด๋ ๋ณด์ฅ์ด ์ด๋ป๊ฒ ๋ผ? | ์ง์ ๋ฑ๊ธ + ๊ณ ํ์ | product_search, coverage_detail | ์ฒซ๋ ๋ถํฐ์๋ณดํ ๊ฐ์ ์กฐ๊ฑดยท๋ณด์ฅ, ๊ณ ํ์ยทํ ์ฆ ๋งฅ๋ฝ ์ ์ง |
| 4 | 4 | ๊ฐํธ์ฌ์ฌ๋ก ๊ฐ์ ํ ์ ์๋ ๊ฑด๊ฐ๋ณดํ๋ ์์ด? | 48์ธ ๋จ์ฑ, ๊ณ ํ์, ํ์๊ธฐ์ฌ | product_search(๊ฐํธ์ฌ์ฌ ๊ฑด๊ฐ) | ๊ฐํธ์ฌ์ฌ ์ํ ์ถ์ฒ, ์ง์ ๋งฅ๋ฝ(์ง์ ยท๋ณ๋ ฅ) ์ ์ง |
| 5. ์๋์ด ์ข ํฉ | 1 | 70์ธ ์๋ฒ์ง์ธ๋ฐ ์ฌ๋ง๋ณด์ฅ์ด๋ ์น์๋ณดํ ๋ ๋ค ์์๋ณด๊ณ ์ถ๋ | ์์ | product_search(์ฌ๋งยท์น์) | 70์ธ ๊ฐ๋ฅ ์ํ ์ถ์ฒ, '์๋ฒ์ง'=๋จ์ฑ ๋งฅ๋ฝ |
| 5 | 2 | ๊ฑด๊ฐํด์ง๋์ข ์ ๋ณดํ๋ 70์ธ์ ๊ฐ์ ๊ฐ๋ฅํด? ๋ณด์ฅ ๋ด์ฉ์ด๋ ์ฐ๊ธ์ ํ ์กฐ๊ฑด ์๋ ค์ค | 70์ธ, ์ง์ ์ํ ๋งฅ๋ฝ | coverage_summary | 70์ธ ๊ฐ์ ๊ฐ๋ฅ ํ์ธ, ๋ณด์ฅยท์ฐ๊ธ์ ํ ์กฐ๊ฑด |
| 5 | 3 | ๋ ๋ ํ์ค๋ฒ์น์๋ณดํ์ 70์ธ์ ๋ณด์ฅ ๋ฒ์๊ฐ ์ด๋ป๊ฒ ๋ผ? | 70์ธ | coverage_summary | 70์ธ ๋ณด์ฅ๋ฒ์(์ถฉ์ ยทํฌ๋ผ์ด), ์ง์ ๋์ด ์ฌ์ฌ์ฉ |
| 5 | 4 | ๋ฐฉ๊ธ ์๊ธฐํ ๋ ์ํ ๋ค ๊ฐ์ ํ๋ฉด ์ ๋ณดํ๋ฃ ํฉ์ณ์ ์ผ๋ง์ฏค ๋์? | 70์ธ ๋จ์ฑ(์๋ฒ์ง), ์ง์ ๋ ์ํ(์ข ์ ยท์ค๋ฒ์น์) | premium_estimate(70, M) 2ํ ํธ์ถ ํ ํฉ์ฐ | ์ง์ ๋งฅ๋ฝ ์ฌ์ฉ. ์๋ฒ์งโ๋จ์ฑ ์๋ ์ธ์. "์ฑ๋ณ ํ์" ๋ฐ๋ณต ๊ธ์ง |
๊ณตํต ๊ฒ์ฆ:
- ๋งค ํด ๋ต๋ณ์ด ์ง์ ์ฑ๋ด ์๋ตยท์ด์ ํด ์ฌ์ฉ์ ์ ๋ ฅ์ ์ฐธ์กฐํ๋์ง(์ฌ์์ฒญยท๋ฌด์ ์์ด) ํ์ธ
- ๊ณ์ฝ์ IDยท์ด๋ฆ์ ์ด๋ฏธ ์กฐํํ ๋ํ์์๋ ๊ฐ์ ์ ๋ณด๋ฅผ ๋ค์ ์๊ตฌํ์ง ๋ง๊ณ , ํ์ํ ์ถ๊ฐ ์ธ์(๋์ดยท์ฑ๋ณ ๋ฑ)๋ง ์ด์ ๋งฅ๋ฝ์์ ์ฑ์์ ๋๊ตฌ ํธ์ถ
6. ๊ตฌํ ์์ธ
6-1. LangGraph 5๋ ธ๋ ํ์ดํ๋ผ์ธ
START โ [input_guardrail] โ [query_rewriter] โ [agent โ tools] โ [output_guardrail] โ END
| ๋ ธ๋ | ์ญํ | ์์ ์๊ฐ |
|---|---|---|
| input_guardrail | ์ ๊ท์(L1) + ์๋ฒ ๋ฉ(L2)์ผ๋ก ์ด์ ์์ฒญ ์ฐจ๋จ | <5ms |
| query_rewriter | "๊ทธ๊ฑฐ ์ผ๋ง์ผ?" ๊ฐ์ ํ์์ง๋ฌธ์ ์ด์ ๋งฅ๋ฝ์ผ๋ก ์ฌ์์ฑ | 0~1s |
| agent | ChromaDB Top-K ๊ฒ์ โ LLM ๋๊ตฌ ํธ์ถ | 1~5s |
| tools | ToolRegistry ๋์ ๋์คํจ์น โ ๋๊ตฌ ์คํ | 10~100ms |
| output_guardrail | PIIยท๊ธ์น์ดยท์ํ์ฝ๋ยท๋๊ตฌ๋ช ์ ๊ฑฐ + ๋ฉด์ฑ ๋ฌธ๊ตฌ ์๋ ์ถ๊ฐ | <2ms |
์ฟผ๋ฆฌ ์ฌ์์ฑ์ Advanced RAG ํต์ฌ ๊ธฐ๋ฒ์ธ Query Transformation์ ํด๋นํจ (์ฐธ๊ณ ).
6-2. ์ํ๊ณต์์ค PDF RAG
๋ณดํ ์ํ๊ณต์์ค์์ 12๊ฐ ์ํ์์ฝ์ + ํ์ค์ฝ๊ด + ํ์ฌ ์ ๋ณด๋ฅผ ์์งํจ. PyMuPDF๋ก ํ ์คํธ ์ถ์ถ โ 500์ ์ฒญํฌ โ ChromaDB ์ธ์ ์คํธ(~1,400 ๋ฒกํฐ). ๋๊ตฌ ๋ฐ์ดํฐ์ ์๋ ์ฝ๊ด ์กฐํญยท๋ฉด์ฑ ๊ท์ ์ RAG๊ฐ ๋ณด์ํจ.
6-3. LLM ์ฐ๋
| ํญ๋ชฉ | ์ค๋ช |
|---|---|
| ์์คํ ํ๋กฌํํธ | 12๊ฐ ์ํ ๋ชฉ๋ก์ด PRODUCTS ๋์ ๋๋ฆฌ์์ ๋์ ๋ฐ์๋จ. ๋๊ตฌ ์ฒด์ด๋ ๊ท์น๋ ํฌํจ |
| ์ฌ๊ณ ๊ณผ์ ํํฐ๋ง | Qwen3 <think> ๋ธ๋ก์ ์คํธ๋ฆฌ๋ฐ ์ค ์ค์๊ฐ ํํฐ๋ง. ์ฌ์ฉ์์๊ฒ ์ต์ข
๋ต๋ณ๋ง ๋
ธ์ถ |
| ๋๊ตฌ ๋ ๋ฒจ ๊ฐ๋ | ๋์ด/์ฑ๋ณ ๋ฑ ํ์๊ฐ ๋ฏธ์ ๊ณต ์ needs_user_input ๋ฐํ โ LLM์ด ๋๋ฌป๋ ๊ตฌ์กฐ |
6-4. ์๋น
| ๋ฐฉ์ | ์ค๋ช | ๋์ |
|---|---|---|
| FastAPI (REST/SSE) | ์น Chat UI + REST API + Admin Dashboard | ์ผ๋ฐ ์ฌ์ฉ์ยท์ด์์ |
| MCP Server (SSE/stdio) | ๋๊ตฌ 54 + ๋ฆฌ์์ค 17 + ํ๋กฌํํธ 8 ๋ ธ์ถ | Claude Desktop, Cursor ๋ฑ |
7. ์ด์
7-1. ๋๊ตฌ ์ถ๊ฐ ์ฒดํฌ๋ฆฌ์คํธ
์ ๋๊ตฌ๋ฅผ ์ถ๊ฐํ ๋ ์๋ ์์๋ฅผ ๋ฐ๋ฆ.
โ ๋๊ตฌ ํจ์ ์์ฑ โ app/tools/ ์๋ ํด๋น ๋ชจ๋์ @tool ํจ์๋ฅผ ์ถ๊ฐํจ. tool.name์ด ์ดํ ๋ชจ๋ ์ฐ๋์ ํค๊ฐ ๋จ.
โก ToolCard ๋ฑ๋ก โ app/tool_search/tool_cards.py์ _CARDS ๋ฆฌ์คํธ์ ์นด๋๋ฅผ ์ถ๊ฐํจ.
| ํ๋ | ๊ท์น |
|---|---|
name |
tool.name๊ณผ ์ ํํ ์ผ์นํด์ผ ํจ |
purpose |
ํ ๋ฌธ์ฅ์ผ๋ก ๋๊ตฌ ๊ธฐ๋ฅ์ ์ค๋ช |
when_to_use |
์ค์ ์ฌ์ฉ์ ๋ฐํ ํจํด์ผ๋ก ์์ฑ |
when_not_to_use |
ํผ๋ ๋๊ตฌ๋ฅผ โ tool_name ์ฌ์ฉ ํ์์ผ๋ก ๋ช
์ |
tags |
๋๋ฉ์ธ ํค์๋ (ํํฐ๋ง์ฉ) |
โข ํผ๋ ์ ๊ด๋ฆฌ โ ๊ธฐ๋ฅ์ด ์ ์ฌํ ๋๊ตฌ๊ฐ ์์ผ๋ฉด ์๋ฐฉํฅ์ผ๋ก when_not_to_use์ CONFUSION_PAIRS์ ๋ฑ๋กํจ.
โฃ ๊ฒ์ฆ โ python -m scripts.eval_tool_recall --compare๋ก Recall@k ํ์ธ.
| ์ฐ๋ ์ง์ | ์๋/์๋ | ๋น๊ณ |
|---|---|---|
| ChromaDB ์๋ฒ ๋ฉ | ์๋ | ์๋ฒ ์์ ์ ํด์ ๋น๊ต โ ๋ณ๊ฒฝ๋ถ๋ง ์ฌ์ธ๋ฑ์ฑ |
| LLM tool description | ์๋ | when_not_to_use๊ฐ description์ ์๋ ์ฃผ์
|
| ๋๊ตฌ ํจ์ | ์๋ | ์นด๋๋ง ์๊ณ ํจ์๊ฐ ์์ผ๋ฉด ๋์ํ์ง ์์ |
CONFUSION_PAIRS |
์๋ | ์ ์ฌ ๋๊ตฌ ์กด์ฌ ์ ๋ฐ๋์ ๋ฑ๋ก |
7-2. Admin Dashboard
CLI ๋์ ๋ธ๋ผ์ฐ์ (/admin/tools)์์ ๋๊ตฌ ๋ ์ง์คํธ๋ฆฌ๋ฅผ ๊ด๋ฆฌํ๋ ์น UI์.
| ๊ธฐ๋ฅ | ์ค๋ช |
|---|---|
| ๋์๋ณด๋ | ๋๊ตฌ ์, ChromaDB ๋ฒกํฐ ์, Registry ๋ฒ์ , ์ํ ๋ชจ๋ํฐ๋ง |
| ToolCard ํธ์ง | purpose, when_to_use, when_not_to_use, tags ์์ โ ์ฆ์ ๋ฐ์ |
| ๋ฒ์ ์ด๋ ฅ | ๋ณ๊ฒฝ ์ด๋ ฅ ์กฐํ, Diff ๋น๊ต, ํน์ ๋ฒ์ ์ผ๋ก ๋กค๋ฐฑ |
| ํต ํ ์คํธ | ์ค์๊ฐ ์ฟผ๋ฆฌ ๊ฒ์, ๋ฐฐ์น Recall ํ๊ฐ, LLM ์คํจ ๋ถ์ |
| ๋๊ตฌ ํด์ | ํ์ธ ๋ชจ๋ฌ โ DELETE โ ChromaDB ๋ฒกํฐ ์ฆ์ ์ญ์ |
| ๋ชจ๋ ํซ๋ฆฌ๋ก๋ | 8๊ฐ ๋ชจ๋ ์ ํ โ ์ฝ๋ ๋ณ๊ฒฝ๋ถ ์๋ฒ ์ฌ์์ ์์ด ๋ฐ์ |
ํต ํ ์คํธ ํญ์์ ์์ ์ ํ Recall@k๋ฅผ ๋น๊ตํ๊ณ , ์คํจ ์ฟผ๋ฆฌ์ ๋ํด LLM์ด ToolCard ๊ฐ์ ์์ ์ ์ํ๋ฏ๋ก ์ฝ๋ ๋ณ๊ฒฝ ์์ด ๊ฒ์ ์ ํ๋๋ฅผ ํ๋ํ ์ ์์.
7-3. ๋ฐํ์ API
curl http://localhost:8080/api/tools # ์ ์ฒด ๋๊ตฌ ๋ชฉ๋ก
curl -X DELETE http://localhost:8080/api/tools/premium_estimate # ๋๊ตฌ ํด์
curl -X POST http://localhost:8080/api/tools/reload-module/premium # ๋ชจ๋ ํซ๋ฆฌ๋ก๋
8. ๊ธฐ์ ์ ํ ๊ทผ๊ฑฐ
8-1. ๋ฒกํฐ DB โ 8๊ฐ ํ๋ณด ๋น๊ต ํ ChromaDB ์ ํ
์ด ํ๋ก์ ํธ๋ ๋ฌด๋ฃ ์คํ์์ค๋ง ์ฌ์ฉ ๊ฐ๋ฅํ๊ณ , HF Spaces Docker ๋จ์ผ ์ปจํ ์ด๋ ๋ฐฐํฌ๊ฐ ํ์ ์กฐ๊ฑด์. ์ด ์กฐ๊ฑด์ผ๋ก 8๊ฐ ๋ฒกํฐ DB๋ฅผ ๋น๊ตยทํํฐ๋งํจ.
Step 1. ์ ๋ฃ/ํด๋ผ์ฐ๋ ์ ์ฉ ์ ์ธ
| DB | ์ ์ธ ์ฌ์ |
|---|---|
| Pinecone | ์์ ๊ด๋ฆฌํ(SaaS ์ ์ฉ), ์์ฒด ํธ์คํ ๋ถ๊ฐ. ํ๋ก๋์ $50/์ ์ต์ ๊ณผ๊ธ (Pinecone Pricing) |
| MongoDB Atlas Search | ๋ฒกํฐ ๊ฒ์์ Atlas ํด๋ผ์ฐ๋ ์ ์ฉ. ์ฐ๊ฐ $5,000~$70,000 (Firecrawl). ๋ก์ปฌ MongoDB CE์๋ ๋ฒกํฐ ๊ฒ์ ๋ฏธ์ง์ |
Step 2. ์คํ์์ค์ด๋ ์ธํ๋ผ ๊ณผ์์ธ ํ๋ณด ์ ์ธ
| DB | ๋ผ์ด์ ์ค | ์ ์ธ ์ฌ์ |
|---|---|---|
| Milvus | Apache 2.0 | ํ๋ก๋์ ๋ถ์ฐ ๋ชจ๋์ K8s ํ์. Standalone ๊ฐ๋ฅํ๋ etcd+MinIO ์์กด์ฑ. ~1,800 ๋ฒกํฐ์ ์ค๋ฒ์์ง๋์ด๋ง (dev.to) |
| OpenSearch | Apache 2.0 | JVM ๊ธฐ๋ฐ ๊ฒ์ ์์ง. ๋ฉ๋ชจ๋ฆฌ 1GB+ ํ์, Docker ๋ด Java ํ๋ก์ธ์ค ์ถ๊ฐ ๋ถ๋ด. ๋ฒกํฐ ๊ฒ์์ knn_vector ํ๋๋ก ์ง์ํ๋, ๊ฒ์ ์์ง ์์ค ์ด์ ๋ณต์ก๋ (Firecrawl) |
| Redis Stack | SSPL / RSALv2 | 2024๋ ๋ถํฐ Redis ๋ผ์ด์ ์ค๊ฐ SSPL๋ก ๋ณ๊ฒฝ๋์ด ์์ ์คํ์์ค๊ฐ ์๋. ๋ฒกํฐ ๊ฒ์์ RediSearch ๋ชจ๋์ ์์กด. ๋ณ๋ Redis ์๋ฒ ํ๋ก์ธ์ค ํ์ (Redis Blog) |
Step 3. ์ต์ข ํ๋ณด โ ChromaDB vs pgvector
| ๊ธฐ์ค | ChromaDB | PostgreSQL + pgvector |
|---|---|---|
| ๋ผ์ด์ ์ค | Apache 2.0 | PostgreSQL License |
| ์ค์น | pip install chromadb |
PostgreSQL ์๋ฒ + CREATE EXTENSION vector |
| ์ํคํ ์ฒ | ์๋ฒ ๋๋ (in-process) | ๋ณ๋ DB ์๋ฒ ํ๋ก์ธ์ค |
| Docker ๋ฐฐํฌ | ์ถ๊ฐ ํ๋ก์ธ์ค ์์ | PostgreSQL ๋ฐ๋ชฌ ํ์ |
| ๋ฉํ๋ฐ์ดํฐ ํํฐ๋ง | O (where ์ ) | O (SQL WHERE) |
| ์ค์๊ฐ upsert | O | O |
| ์์์ฑ | O (SQLite + parquet) | O |
| ํ๊ตญ์ด ์ปค์คํ ์๋ฒ ๋ฉ | ์ง์ ์ ๋ฌ ๊ฐ๋ฅ | ์ง์ ์ ๋ฌ ๊ฐ๋ฅ |
| ์ด์ ๋ณต์ก๋ | ์ต์ (ํ์ผ ๊ธฐ๋ฐ) | ์ค๊ฐ (DB ๊ด๋ฆฌ ํ์) |
ChromaDB๋ฅผ ์ ํํ ์ด์ :
Docker ๋จ์ผ ์ปจํ ์ด๋ ์ ํฉ์ฑ โ HF Spaces๋ ํ๋์ Docker ์ปจํ ์ด๋๋ก ์๋นํจ. ChromaDB๋ ์๋ฒ ๋๋ ๋ชจ๋๋ก FastAPI ํ๋ก์ธ์ค ์์์ ๋์ํ๋ฏ๋ก ๋ณ๋ DB ํ๋ก์ธ์ค๊ฐ ํ์ ์์. pgvector๋ PostgreSQL ๋ฐ๋ชฌ์ ํจ๊ป ๋์์ผ ํจ.
์ธํ๋ผ ์ ๋ก โ
pip install chromadbํ ์ค๋ก ๋๋จ. DB ์ค์ , ์คํค๋ง ์์ฑ, ์ปค๋ฅ์ ํ ๊ด๋ฆฌ๊ฐ ์์.์ค์๊ฐ upsert โ ToolCard ์์ ์ ์๋ฒ ์ฌ์์ ์์ด ์ฆ์ ๋ฒกํฐ๋ฅผ ๊ฐฑ์ ํด์ผ ํจ. ChromaDB๋
collection.upsert()๋ก ํด๊ฒฐ๋จ. FAISS๋ ์ธ๋ฑ์ค ์ ์ฒด๋ฅผ rebuild ํด์ผ ํจ.๊ท๋ชจ ์ ํฉ์ฑ โ ๋๊ตฌ 54๊ฐ ร ํ๋ 7๊ฐ = ~1,800 ๋ฒกํฐ. 10M ๋ฒกํฐ ๋ฏธ๋ง ํ๋กํ ํ์ ์์ ChromaDB ๊ถ์ฅ (Firecrawl) (dev.to).
LangChain ์ํ๊ณ ํตํฉ โ LangGraph/LangChain๊ณผ ๋ค์ดํฐ๋ธ ์ฐ๋์ด ๊ฒ์ฆ๋์ด ์์ (TrueFoundry).
์ค์ผ์ผ ์์ ์๋๋ฆฌ์ค: ๋ฒกํฐ๊ฐ 10M์ ๋๊ฑฐ๋ ๋ฉํฐ๋ ธ๋ HA๊ฐ ํ์ํด์ง๋ฉด Qdrant(Rust ๊ธฐ๋ฐ, ๊ณ ์ฑ๋ฅ ํํฐ๋ง) ๋๋ Milvus(K8s ๋ถ์ฐ)๋ก ๋ง์ด๊ทธ๋ ์ด์ ํ๋ ๊ฒ์ด ์ผ๋ฐ์ ๊ฒฝ๋ก์ (Firecrawl).
8-2. ์๋ฒ ๋ฉ ๋ชจ๋ธ โ multilingual-e5-large
| ๊ธฐ์ค | e5-base | e5-large | OpenAI ada-002 |
|---|---|---|---|
| Kor-IR NDCG@10 | โ | 80.35 (OSS ์ต์์) | โ |
| Mr. TyDi ํ๊ตญ์ด MRR@10 | 55.8 | 61.6 (+10%) | โ |
| ๋น์ฉ | ๋ฌด๋ฃ ๋ก์ปฌ | ๋ฌด๋ฃ ๋ก์ปฌ | $0.13/1M tokens |
| ์ถ๋ก ์๋ | ~5ms | ~10ms | ๋คํธ์ํฌ ์์กด |
Kor-IR ๋ฒค์น๋งํฌ ์คํ์์ค ์ต์์.
๋น๋์นญ ๊ฒ์ ์ "query: " / "passage: " ํ๋ฆฌํฝ์ค ํ์ (๋
ผ๋ฌธ).
๋ก์ปฌ ์ถ๋ก (~10ms/์ฟผ๋ฆฌ)์ผ๋ก ์ธ๋ถ API์ ์์กดํ์ง ์์ (๋ชจ๋ธ ์นด๋).
8-3. Tool Card ํ์ ๊ทผ๊ฑฐ
| ์ถ์ฒ | ํต์ฌ ๊ธฐ์ฌ |
|---|---|
| Tool-DE (Lu et al., 2025) | ๋๊ตฌ ๋ฌธ์ ํ์ฅ์ผ๋ก NDCG@10 +6~7ppt, Recall@10 +10ppt |
| Re-Invoke (Google, EMNLP 2024) | ํฉ์ฑ ์ฟผ๋ฆฌ ์์ฑ์ผ๋ก nDCG@5 ์ ์๋ฏธ ํฅ์ |
| ToolBench (ICLR 2024) | ๋๊ตฌ ์ ์ฆ๊ฐ ์ cross-reference๊ฐ ์ ํ๋ ์ ํ๋ฅผ ๋ฐฉ์ง |
| RAG-MCP (WRITER, 2025) | ๋ฉํ๋ฐ์ดํฐ ๊ธฐ๋ฐ ์ธ๋ฑ์ฑ โ ํ ํฐ 50%+ ์ ๊ฐ |
9. ์๋ ค์ง ํ๊ณ ๋ฐ ๊ณ ๋ํ ๋ฐฉํฅ
| ํ๊ณ | ํ์ | ๋ฐฉํฅ |
|---|---|---|
| when_to_use ์ค๋ฒํ | product_search์ ํ ๋๊ตฌ ์์ญ ๋ฐํ๊ฐ ์๋ฒ ๋ฉ์ ํฌ์ํจ | ์์ ์ํ ๊ฒ์ ๋ฐํ๋ง ์ ์ง |
| cross-reference ๋๋ฝ | renewal_projection โ renewal_notice ์๋ฐฉํฅ ๊ฐ์ด๋ ๋ถ์ฌ | when_not_to_use ์๋ฐฉํฅ ๋ณด์ |
| ์๋ ์์ฑ ํ๊ณ | 54๊ฐ ร ~7๊ฐ = ~380๊ฐ when_to_use๋ฅผ ์๋ ๊ด๋ฆฌ ์ค | Re-Invoke ๋ฐฉ์ LLM ํฉ์ฑ ์ฟผ๋ฆฌ ์๋ ์์ฑ |
| ์ ์ no-call ์๊ณ๊ฐ | tool-call min(0.867)๊ณผ no-call max(0.877)์ด ๊ฒน์นจ | Reranker 2๋จ๊ณ ๋์ |
Quick Start
# 1. ์ค์น
python -m venv .venv && source .venv/bin/activate
pip install -e .
# 2. ํ๊ฒฝ๋ณ์ (.env)
OPENROUTER_API_KEY=sk-or-v1-your-key
OPENROUTER_MODEL=qwen/qwen3-14b
EMBEDDING_MODEL=intfloat/multilingual-e5-large
# 3. ChromaDB ์ด๊ธฐํ (์ต์ด 1ํ)
python scripts/init_vectordb.py
# 4. ์๋ฒ ์คํ
python run.py # FastAPI โ http://localhost:8080
python run_mcp.py # MCP Server
python run_mcp.py --inspect # MCP Inspector UI
# 5. ๋๊ตฌ ๋ผ์ฐํ
ํ๊ฐ
python -m scripts.eval_tool_recall --compare
ํ๋ก์ ํธ ๊ตฌ์กฐ
app/
โโโ main.py # FastAPI (REST/SSE + think ํํฐ๋ง)
โโโ config.py # Settings + ์๋ฒ ๋ฉ ๋ชจ๋ธ ์ฑ๊ธํค
โโโ graph/ # LangGraph 5๋
ธ๋ ํ์ดํ๋ผ์ธ
โ โโโ builder.py # ๊ทธ๋ํ ๋น๋ + ๋์ ๋๊ตฌ ๋์คํจ์น
โ โโโ nodes.py # agent ๋
ธ๋ (ChromaDB ๋ผ์ฐํ
+ LLM)
โ โโโ guardrails.py # ์
๋ ฅ(L1+L2) / ์ถ๋ ฅ ๊ฐ๋๋ ์ผ
โ โโโ query_rewrite.py # ํ์์ง๋ฌธ ์ฌ์์ฑ
โโโ tools/ (54๊ฐ, 8๋ชจ๋) # product / premium / coverage / underwriting
โ โโโ __init__.py # ToolRegistry (ํซ๋ฆฌ๋ก๋)
โ โโโ data.py # 12๊ฐ ์ํ ๋ฐ์ดํฐ + ์์คํ
ํ๋กฌํํธ
โโโ tool_search/ # ChromaDB ๋ฉํฐ๋ฒกํฐ ๋ผ์ฐํ
โ โโโ embedder.py # ์๋ฒ ๋ฉ + Top-K ๊ฒ์
โ โโโ tool_cards.py # 54๊ฐ ToolCard
โ โโโ toolcard_store.py # ToolCard JSON ์์ํ + ๋ฒ์ ์ด๋ ฅ
โโโ rag/ # ์ํ๊ณต์์ค PDF RAG
โ โโโ retriever.py # ์ธ์ ์คํธ + ๊ฒ์
โ โโโ splitter.py # ํ๊ตญ์ด ๋ฌธ์ฅ๊ฒฝ๊ณ ์ฒญํฌ ๋ถํ
โโโ mcp_server/ # MCP ํ๋กํ ์ฝ ์๋ฒ + Inspector
templates/
โโโ index.html # ์ฑ๋ด Chat UI (์ํ ์นดํ๋ก๊ทธ, ์๋๋ฆฌ์ค)
โโโ admin_tools.html # Tool Admin Dashboard
scripts/
โโโ init_vectordb.py # ChromaDB ์ด๊ธฐํ
โโโ eval_tool_recall.py # Recall@k / MRR ํ๊ฐ
๋๊ตฌ ์นดํ๋ก๊ทธ (54๊ฐ)
| ๋ชจ๋ | ์ | ์ฃผ์ ๊ธฐ๋ฅ |
|---|---|---|
| product | 10 | ์ํ ๊ฒ์/์กฐํ/๋น๊ต, ํน์ฝ, FAQ |
| premium | 8 | ๋ณดํ๋ฃ ์ฐ์ถ/๋น๊ต, ํ๋, ๊ฐฑ์ ์ถ์ |
| coverage | 9 | ๋ณด์ฅ ์์ฝ/์์ธ, ๊ธ๋ถ ๊ธ์ก |
| underwriting | 12 | ๊ฐ์ ์ฌ์ฌ, ๋ น์์ ๋ฃฐ, ์ง์ ์ํ๋ |
| compliance | 6 | ์ค๋ฒ ๋ฉํธ, ๊ธ์น์ด, PII ๋ง์คํน |
| claims | 4 | ์ฒญ๊ตฌ ์ ์ฐจ, ์๋ฅ, ๊ณ์ฝ๊ด๋ฆฌ |
| customer_db | 3 | ๊ณ ๊ฐ ๊ฒ์, ๊ณ์ฝ ์กฐํ |
| rag_tools | 2 | ์ฝ๊ด/์์ฝ์ RAG ๊ฒ์ |
๊ธฐ์ ์คํ
| ์นดํ ๊ณ ๋ฆฌ | ๊ธฐ์ | ์ญํ |
|---|---|---|
| LLM ์ค์ผ์คํธ๋ ์ด์ | LangGraph | ReAct ๊ทธ๋ํ, ๋ฉํฐํด, ์กฐ๊ฑด๋ถ ๋ถ๊ธฐ |
| LLM | OpenRouter (qwen/qwen3-14b) | ๋ค์ค ๋ชจ๋ธ ๋ผ์ฐํ |
| ๋ฒกํฐ DB | ChromaDB | ๋๊ตฌ ๋ผ์ฐํ + RAG ๊ฒ์ |
| ์๋ฒ ๋ฉ | multilingual-e5-large (1024d) | ํ๊ตญ์ด ๋น๋์นญ ๊ฒ์ |
| API ์๋ฒ | FastAPI | REST + SSE ์คํธ๋ฆฌ๋ฐ |
| MCP ์๋ฒ | FastMCP | Claude Desktop/Cursor ์ฐ๋ |
| PDF ํ์ฑ | PyMuPDF | ์ฝ๊ด/์์ฝ์ ํ ์คํธ ์ถ์ถ |
| ๊ณ ๊ฐ DB | SQLite3 | ๊ณ ๊ฐ/๊ณ์ฝ ์๋ฎฌ๋ ์ด์ |
References
| ์ฃผ์ | ์ถ์ฒ |
|---|---|
| ๋๊ตฌ ์ ์ฆ๊ฐ ์ ์ ํ๋ ์ ํ | How many tools can an AI Agent have? |
| RAG-MCP: ๋๊ตฌ ๊ฒ์ ํ LLM์ ์ ๋ฌ | WRITER Engineering |
| Tool Document Expansion (Tool-DE) | arXiv 2510.22670 |
| ํฉ์ฑ ์ฟผ๋ฆฌ ๊ธฐ๋ฐ ๋๊ตฌ ๊ฒ์ (Re-Invoke) | EMNLP 2024 |
| ๋๊ท๋ชจ ๋๊ตฌ ๋ฒค์น๋งํฌ (ToolBench) | ICLR 2024 |
| ๋ฒกํฐ DB ๋น๊ต (2025) | Firecrawl ยท dev.to ยท TrueFoundry |
| ๋ฒกํฐ DB ๊ฐ๊ฒฉ ๋น๊ต | Actian ยท Pinecone Pricing |
| Redis ๋ฒกํฐ DB ๋น๊ต | Redis Blog |
| ํ๊ตญ์ด IR ๋ฒค์น๋งํฌ (Kor-IR) | GitHub |
| multilingual-e5-large | Hugging Face ยท arXiv 2402.05672 |
| Multi-vector retrieval | Pinecone |
| Query Rewriting / Advanced RAG | Prompting Guide |
| LangGraph ๊ณต์ ๋ฌธ์ | LangChain |