Skip to content

feat(infra): 외부 리소스 조사 3 트랙 — context7 / web-fetch (Playwright) / Anthropic web_search #62

@hagyutae

Description

@hagyutae

배경

에이전트들이 작업 도중 외부 리소스 조사가 필요한 케이스가 발생:

  • 라이브러리 / 프레임워크 사용법 / API spec 확인 (코드 작업 빈번)
  • 사용자가 제공한 URL 페이지 내용 파악
  • 일반 web search (사용자 의도 분석 / 시장 조사 / 외부 정보)

이를 일관된 패턴으로 cover 하기 위해 3 트랙으로 준비.

3 트랙

트랙 1: context7 (라이브러리 / 프레임워크 공식 docs)

용도: 코드 작업 중 가장 빈번한 기술 질의. 공식 docs 한정이라 outdated 블로그 / 잘못된 tutorial 회피.

기술: context7 (Upstash) — 이미 MCP 서버 (https://mcp.context7.com/mcp streamable HTTP). wrapper 0 — 우리 에이전트가 외부 MCP 에 직접 connect.

도구 (context7 가 노출):

  • resolve-library-id(name) → context7 lib id
  • get-library-docs(id, topic?, version?) → markdown

통합: 에이전트 config/base.yamlmcp_servers 에 추가. lifespan 에서 StreamableMCPClient.connect → 도구 LLM 에 bind_tools.

호출 주체: A / ENG / QA (코드 작업 직접) + L (라이브러리 메타 질의 시 위임 가능). M3+ 의존.

트랙 2: Playwright 기반 web-fetch MCP

용도: 사용자가 URL 제공한 페이지 내용 파악. JS-heavy 사이트 / SPA / dynamic content 까지 처리 (httpx + trafilatura 만으론 부족한 케이스).

기술: 우리 컨테이너 신설 — mcp/web-fetch/. Playwright (chromium headless) + readability/trafilatura.

도구 (예상):

  • web.fetch(url, format="markdown"|"text"|"html") → PageContent{title, content, url}
  • web.fetch_with_render(url, wait_for?: str) (JS 실행 + 특정 셀렉터 대기)

구현 방식 — adapter 패턴 (#36/#37 일관):

  • 빠른 path: httpx + trafilatura (정적 HTML)
  • 적응적 fallback: playwright (JS 렌더 필요 추정 시)

컨테이너: chromium binary 200-400MB → 이미지 무거움. mcp/web-fetch/ 별도 분리해 다른 MCP 영향 X.

비-스코프: 임의 사이트 자동 검색 (Google scrape 등) — bot detection / ToS / 안정성 risk 로 회피.

트랙 3: Anthropic web_search (Claude API native tool)

용도: 일반 web search (사용자 의도 분석 / 시장 조사 / 외부 정보). 우리가 backend 운영 X — Anthropic 이 SaaS 로 제공.

기술: Claude API 의 web_search_20250305 tool type. LLM 호출 시 tools 배열에 추가.

{
  "model": "claude-opus-4-7",
  "tools": [{"type": "web_search_20250305", "name": "web_search", "max_uses": 5}],
  "messages": [...]
}

구현: backend 0. langchain-anthropic 또는 anthropic SDK 의 tools 배열로 직접. LLM 호출 시 자동 활성.

비용: Claude API 토큰 비용에 포함 (별 SaaS 비용 X).

제약:

  • Claude 종속 — 다른 LLM (Gemini / GPT 등) 갈아탔을 때 호환 X
  • max_uses 별 비용 / latency 관리 필요

호출 주체: 모든 에이전트 (LLM 호출 시 자동 활성, L 통과 X).

트랙 비교 표

트랙 backend 우리 컨테이너? 호출 주체 사용 시점
context7 Upstash SaaS (MCP) X (외부 직접) A / ENG / QA / L 라이브러리 docs 조회
web-fetch (Playwright) 자체 운영 mcp/web-fetch/ P / L (URL 받았을 때) 임의 페이지 내용 파악
Anthropic web_search Anthropic SaaS (LLM tool) X (LLM 내장) 모든 에이전트의 LLM 일반 web search

모듈 / 파일 변경

docs/external-research.md               # 신설 (시스템 설계 — 본 이슈 본문의 트랙 정리)

mcp/web-fetch/                          # 신설 (트랙 2)
├── Dockerfile (python:3.13-slim + chromium)
├── pyproject.toml (playwright, trafilatura)
├── src/web_fetch_mcp/
│   ├── adapters/
│   │   ├── base.py                    # FetchOps ABC
│   │   ├── httpx_/                    # 정적 HTML
│   │   └── playwright_/               # JS 렌더
│   ├── factory.py
│   └── tools/web.py
└── scripts/verify_sandbox.{sh,py}

shared/src/dev_team_shared/web_fetch/   # 신설 SDK (트랙 2)
├── schemas/
├── tool_names.py
├── _ops_client.py
└── client.py

agents/<name>/config/base.yaml          # mcp_servers 에 context7 추가 (트랙 1, 호출 주체별)

# 트랙 3 (Anthropic web_search) 은 backend 0
# - shared/llm/ 의 ChatModel 호출 시 tools 배열에 web_search 추가하는 helper
# - 또는 각 에이전트 graph 에서 LLM bind_tools 시 함께 전달

본 이슈 스코프

트랙 본 이슈에 포함
1. context7 ✅ — config/base.yaml 에 mcp_servers 추가 + 에이전트 lifespan 의 multi-MCP connect 지원
2. web-fetch (Playwright) ✅ — mcp/web-fetch/ 신설 + SDK + sandbox
3. Anthropic web_search ✅ — shared/llm/ 의 helper or agent graph 에 옵션 추가
(외 일반 web search — Brave/Tavily 등) ❌ — M5+ 별 이슈

비-스코프

검증

  • 트랙 1: context7 MCP connect → resolve-library-id / get-library-docs 라운드트립
  • 트랙 2: mcp/web-fetch/ 컨테이너 부팅 + httpx fetch + Playwright fetch 양쪽 통과
  • 트랙 3: Claude API 의 web_search_20250305 tool 활성 + 결과 ChatModel 응답에 reflect
  • 단위 테스트 (트랙 2)
  • sandbox 검증 (트랙 2)

의존

후속 작업 흐름

본 이슈 머지 후 각 agent wiring 이슈에서 운영 지침 작성:

flowchart TB
    A["#62 (본 이슈)<br/>docs/external-research.md<br/>+ backend (mcp/web-fetch / web_search helper)"]
    A --> L["L wiring 이슈<br/>multi-MCP (context7) + resources/external-research-guide.md"]
    A --> AA["A wiring (#45)<br/>resources/external-research-guide.md"]
    A --> EQ["ENG / QA (M5+)<br/>각자 resources/external-research-guide.md"]
Loading

agent 별 가이드는 같은 트랙들을 그 agent 의 책임 / 사용 시점 / 우선순위에
맞춰 운영 지침으로 정리 (기존 패턴: docs/doc-store-schema.md
agents/primary/resources/wiki-authoring-guide.md reference).

관련

  • root CLAUDE.md "통신 프로토콜 우선순위" — MCP 우선
  • proposal §2.5 — L 의 read-side 단일 창구 (context7 도 동일 카테고리)
  • docs/ — 사람용 시스템 설계 문서 위치 (본 이슈의 산출물)
  • agents/<name>/resources/ — agent 별 LLM 운영 지침 위치 (별 이슈)

Metadata

Metadata

Assignees

No one assigned

    Labels

    enhancementNew feature or request

    Type

    No type
    No fields configured for issues without a type.

    Projects

    Status

    No status

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions