Claude Code 에 MCP 로 꽂아 쓰는 펜테스트 오케스트레이터. 17개 에이전트가 정찰부터 보고서까지 직접 돌리고, 60개 큐레이션 프로브 + 200개 외부 보안 툴 래퍼로 OWASP 주스샵 같은 SPA 에서 63% 챌린지 솔브률을 기록한다.
한 줄로 보면.
pentest-ai 는 "AI 에이전트한테 펜테스트(침투 시험)를 통째로 맡기는" 오픈소스 도구다. PyPI 에서 pip install ptai 한 줄이면 끝이고, 실행 명령도 ptai start https://target.example.com 한 줄이면 된다. 그러면 도구가 알아서 포트 스캔 → 로그인 → 웹 취약점 탐색 → 액티브 디렉토리(AD) 점령 → 클라우드 권한 상승 → 공격 체인 조합 → 검증 PoC 실행 → 마크다운/HTML/PDF 보고서 작성까지 끝낸다.
특이한 점은 LLM 을 두뇌로 쓰지만 탐지 자체는 "사람이 만든 결정론적 프로브"가 한다는 설계다. 즉 LLM 이 시키지 않아도 같은 60개 프로브가 똑같이 돌아가고, LLM 은 결과를 보고 다음에 뭘 칠지 고민하는 코디네이터 역할만 맡는다. 그래서 API 키 없이 Claude Code 의 구독만으로도 쓸 수 있다.
트렌드시프트 12위에 오른 이유.
외부 보안 컨설팅은 한 번에 수천만 원 + 2주 일정. AppSec 팀은 ZAP·Burp·Nuclei 같은 도구를 직접 돌려야 하는데 도구마다 인터페이스가 다르고 결과가 노이즈투성이다. pentest-ai 는 "200개 보안 도구를 LLM 이 알아서 골라 쓰고, 결과를 한 보고서로 합쳐 주는" 인공지능 컨설턴트 한 명을 노트북에 띄우는 것에 가깝다.
경쟁 도구 대비 차별점은 명확하다.
대부분의 자동 스캐너(ZAP, Nuclei) 는 로그인 페이지에서 멈춘다. 인증 세션을 유지하지 못해서 그렇다. pentest-ai 는 auth_profile 로 로그인 시퀀스를 정의하면 JWT(JSON Web Token) 를 뽑아 모든 후속 프로브에 자동 첨부한다. 그래서 "회원 영역의 SQL 인젝션"처럼 인증 뒤에만 보이는 버그를 잡는다.
일반 스캐너는 "여기 취약점일 수도?" 후보 40개를 던지고 사람이 골라야 한다. pentest-ai 는 poc_validator 에이전트가 발견된 모든 취약점에 비파괴(non-destructive) 증명 코드(Proof of Concept)를 실제로 돌려 본다. 통과한 것만 보고서에 올라가니 거짓 양성률(False Positive) 이 0% 에 가깝다.
Path 1 (MCP) 로 설치하면 LLM 비용은 이미 결제 중인 Claude Pro/Max 구독으로 처리되고, pentest-ai 는 도구만 제공한다. 즉 OpenAI 도, Anthropic API 도 따로 안 사도 된다. CI/CD 처럼 자동화가 필요하면 Path 3 (Standalone) 로 별도 API 키를 쓰면 된다.
OWASP 주스샵에서 ptai 88개 finding(46개 critical+high), ZAP 593개(critical+high 0개·FP 47%), Nuclei 1개. 번호도 raw 결과도 git 에 들어가 있어서 직접 재현할 수 있다. "98.7% 탐지" 같은 검증 불가능한 마케팅 문구를 피한다.
recon(정찰)/web/api_security/ad/cloud/mobile/browser/credential_tester/privesc/vuln_scanner/exploit_chain/poc_validator/detection/report/llm_redteam/social_engineer/wireless 17 종 전문 에이전트가 각자 분야를 맡고, 그 아래로 200개 외부 도구(nmap, sqlmap, hydra, hashcat, BloodHound 등) 래퍼와 60개 사내 큐레이션 프로브가 매달려 있다.
패키지 매니페스트(pyproject.toml)에서 직접 뜯어본 의존성.
pentest-ai 는 Python 3.10+ 단일 언어 패키지로, 코어 의존성은 의도적으로 가볍게 유지하고 무거운 기능들은 optional-dependencies 그룹으로 분리해 둔다. 사용자가 필요한 surface 만 골라 깔 수 있도록.
@mcp.tool() 데코레이터 하나로 함수를 LLM 노출 도구로 등록.ptai start, ptai mcp 등 50+ 서브커맨드).AWS/Azure/GCP 권한 점검을 할 때만 필요. 세 거대 클라우드의 IAM·미설정·K8s RBAC·서버리스 권한 상승 등을 다룸. pip install ptai[cloud].
LiteLLM 어댑터를 통해 OpenRouter·Azure·DeepSeek·Groq·Mistral·Together AI·Bedrock·Vertex AI·Cohere 등 어떤 LLM API 든 같은 인터페이스로 호출. 핵심 설치를 가볍게 유지하려고 옵션으로 분리.
MCP 대신 HTTP REST 로 통합하고 싶을 때. ptai serve --port 8888 으로 띄우면 /engagements, /findings, WebSocket 실시간 이벤트 스트림이 열린다.
BrowserAgent 가 헤드리스 크롬으로 DOM·XHR·보안 헤더를 직접 분석할 때. 단순 HTTP 만으로는 SPA(Single Page Application) 의 동적 라우트·XHR 호출이 안 잡혀서 별도 분리.
Cloudflare Turnstile, 브라우저 핑거프린팅 같은 안티봇 우회가 필요한 정찰용. scrapling install --force 로 별도 브라우저 바이너리 추가 다운로드.
관측가능성(observability) 을 켤 때. Phoenix, Jaeger, Tempo, Datadog, Honeycomb 등 OTLP 받는 어떤 백엔드로도 trace 송신. LLM 호출 + 도구 실행이 trace span 으로 자동 기록.
pentest-ai 자체에 포함되지 않은 200+ 외부 CLI 들. ptai setup --tier core 로 6 개 핵심만, --tier recommended 로 30 개, --tier full 로 전부 설치. 엔터프라이즈처럼 "모든 도구를 시스템에 깔지 못하게" 막혀 있어도 해당 도구를 호출하는 경로만 자동으로 건너뛰는 우아한 폴백이 있다.
390 줄짜리 오케스트레이터 가 어떻게 17 에이전트를 굴리는가.
전체 흐름을 ASCII 로 그리면 이렇다. 화살표는 데이터 흐름이고, 각 박스는 별도 모듈이다.
┌──────────────────────────────────────────────────────────────┐
│ Claude Code / Cursor / Codex (MCP client, LLM 두뇌 역할) │
└────────────────────────────┬─────────────────────────────────┘
│ JSON-RPC over stdio
▼
┌──────────────────────────────────────────────────────────────┐
│ mcp_server/server.py FastMCP @mcp.tool() × 49 도구 │
│ start_engagement / list_tools / run_tool / run_probe / ... │
└────────────────────────────┬─────────────────────────────────┘
│
▼
┌──────────────────────────────────────────────────────────────┐
│ engine/orchestrator.py AgentOrchestrator │
│ ───────────────────────────────────────────────────────── │
│ PHASE_ORDER = [recon, web, ad, cloud, mobile, chaining, │
│ validation, detection, report] │
│ │
│ for phase in PHASE_ORDER: │
│ agent.run(scope, rate_limiter, auth, llm) │
└────────────────────────────┬─────────────────────────────────┘
│
┌────────────────────┼────────────────────┐
▼ ▼ ▼
┌─────────┐ ┌──────────┐ ┌──────────┐
│ recon │ │ web │ │ ad │
│ agent │ │ agent │ │ agent │
└────┬────┘ └────┬─────┘ └────┬─────┘
│ │ │
▼ ▼ ▼
┌─────────────────────────────────────────────────┐
│ tools/registry.py ToolRegistry (200+ wrap) │
│ + SecurityTool 데이터클래스 — command·parser │
│ + BLOCKED_ARG_KEYS — 인자 화이트리스트 │
│ + intensity-aware cache │
└────────────────────────┬────────────────────────┘
│ subprocess.run / asyncio
▼
┌──────────────────┐
│ 외부 보안 도구 │
│ nmap, sqlmap, │
│ hydra, impacket │
└────────┬─────────┘
▼
┌──────────────────────────────────────────┐
│ engine/findings_db.py (aiosqlite) │
│ scope-guarded · deduplicated · evidence │
└────────────────────┬─────────────────────┘
│
┌──────────────┼──────────────┐
▼ ▼ ▼
┌─────────┐ ┌──────────┐ ┌──────────┐
│ chain │ │ poc_val. │ │ detection│
│ agent │ │ agent │ │ agent │
└────┬────┘ └────┬─────┘ └────┬─────┘
└──────────────┼───────────────┘
▼
┌───────────────┐
│ report agent │ md/html/pdf/SARIF/JUnit
└───────────────┘
engine/orchestrator.py 의 PHASE_ORDER 리스트는 9 단계가 무조건 이 순서로 실행된다. 한 단계가 끝나야 다음 단계가 들어가고, 단계마다 findings DB 에 결과가 쌓인다. "recon 이 끝나야 web 이 의미가 있고, web 이 끝나야 chain 이 의미가 있다" 는 펜테스트 방법론이 코드 구조로 그대로 박혀 있다.
건물 침입 시뮬레이션과 같다. 먼저 외부에서 빙 둘러보며 창문·문 위치 파악(recon) → 자물쇠 열어 보고(web/ad) → 들어가서 금고 위치 파악(privesc) → 금고 따기(poc_validator) → CCTV 가 무엇을 잡았어야 했는지 보고(detection) → 최종 보고서 작성(report). 순서가 거꾸로면 의미가 없다.
READme 의 다섯 강조점 중 가장 중요한 설계 결정. LLM 이 없어도 같은 60 개 프로브가 똑같이 돌아간다. LLM 은 "이 finding 으로 다음에 어디를 칠까" 같은 추론만 담당하고, 실제 탐지 로직은 사람이 큐레이션한 결정론적 파이썬 함수다.
최근 연구(ARTEMIS, DARPA AICC Atlantis, xOffense)에 따르면 완전 자율 LLM 펜테스트 에이전트는 챌린지의 21~31% 만 끝낸다. 사람이 중간 개입하는 휴먼-인-더-루프(HITL) 셋업은 64% 까지 올라간다. "LLM 이 알아서 다 해줄 거야" 라는 가정으로 만든 도구는 실전에서 안 잡히는 게 많다.
pentest-ai 는 의도적으로 LLM 을 "지휘"에만 쓴다. SQL 인젝션·XSS·XXE·JWT alg:none 같은 60 개 패턴은 파이썬으로 결정론적으로 짜여 있고, LLM 은 그것들이 만든 finding 을 보고 다음 phase 를 결정한다. 결과적으로 같은 타깃에서 같은 결과가 나오게(reproducible) 만들었다.
오펜시브 도구의 가장 위험한 실패 모드는 "허락받지 않은 시스템을 공격해 버리는 것". pentest-ai 는 engine/scope.py 의 ScopeEnforcer 가 모든 도구 호출 직전에 타깃 호스트가 사전에 선언된 범위 안인지 검증한다. strict_scope=true 옵션을 켜면 HTTP 302 리다이렉트도 따라가지 않는다. 공격자가 http://victim.com/redirect?url=http://attacker.com 같은 트릭으로 스캔을 빼돌릴 수 없다.
ScanProfile.from_intensity(intensity) 가 stealth/safe/normal/aggressive 4 단계 강도에 따라 RPS(초당 요청 수)·동시성·재시도 정책을 동적으로 잡아 준다. 운영 중인 서비스를 다운시키지 않으려는 안전장치. HTTP 429 응답을 받으면 Retry-After 헤더를 존중한다(0.15.1 새 기능).
tools/registry.py 의 BLOCKED_ARG_KEYS 집합은 LLM 이 도구에 절대 못 넣게 막아야 하는 위험한 인자들이다.
BLOCKED_ARG_KEYS = frozenset({
"script", "script-args", "output", "oN", "oX", "oG", "oA",
"exec", "eval", "command", "cmd", "shell", "system",
"upload", "download", "write", "config",
})
LLM 이 nmap --script vulners {target} 처럼 임의의 NSE 스크립트를 실행하려 하면 차단된다. 키 이름 검증(^[a-zA-Z0-9_-]+$) 과 값 검증(;|&\`$ 등 셸 메타문자 거부) 까지 더해서 LLM 프롬프트 인젝션이 셸 인젝션으로 번지는 경로를 막는다.
엔게이지먼트 진행 중 Ctrl+C 를 600 밀리초 안에 두 번 누르면 오케스트레이터가 멈추고 REPL 로 떨어진다. step(다음 한 phase 만), inspect findings, inject <instruction>(LLM 에 추가 지시), skip, resume, abort. 사람이 중간에 개입할 수 있게 명시적으로 설계되어 있다.
35,000 줄짜리 코드베이스를 조감하면.
pentest-ai/
├── cli/ # ptai CLI 진입점 (Typer)
│ ├── main.py # 42개 서브커맨드 (3,154 줄)
│ ├── auth.py # 인증 프로필 관리
│ ├── menu.py # 비-LLM 사용자용 numeric 메뉴
│ ├── install_wizard.py # 200 개 외부 도구 설치 마법사
│ └── mcp_setup.py # 다른 MCP 클라이언트 자동 설정
│
├── mcp_server/ # FastMCP 서버 (LLM 노출 surface)
│ ├── server.py # @mcp.tool() 전체 모듈 합산 약 57개 (1,821 줄)
│ ├── auth.py
│ └── security_tools.py
│
├── api/ # FastAPI HTTP 대안
│ ├── server.py
│ └── static/ # 로컬 웹 대시보드
│
├── engine/ # 핵심 비즈니스 로직
│ ├── orchestrator.py # 9-phase 코디네이터 (390 줄)
│ ├── agent_loop.py # LLM 에이전트 루프 (456 줄)
│ ├── findings_db.py # SQLite + evidence storage
│ ├── scope.py # ScopeEnforcer
│ ├── auth_handler.py # JWT/cookie/Basic auth 핸들링
│ ├── rate_limiter.py # ScanProfile (stealth..aggressive)
│ ├── playbook.py # YAML 플레이북 실행기
│ ├── hitl.py # Ctrl+C 두 번 REPL
│ ├── cvss.py # CVSS v3.1 점수 계산
│ ├── sarif.py # SARIF 2.1.0 출력
│ ├── junit_xml.py # JUnit XML 출력
│ ├── tracing.py # OpenTelemetry 통합
│ ├── llm/ # LLM 클라이언트 (LiteLLM, Anthropic, OpenAI, Ollama)
│ └── probes/ # 60 개 큐레이션 프로브 (SPA-aware)
│
├── agents/ # 17 개 전문 에이전트
│ ├── base.py # BaseAgent 추상 클래스
│ ├── recon/ # 정찰
│ ├── web/ # 웹 + spa_probes.py
│ ├── api_security/ # OpenAPI/GraphQL OWASP API Top 10
│ ├── ad/ # Active Directory
│ ├── cloud/ # AWS/Azure/GCP
│ ├── mobile/, wireless/, browser/
│ ├── credential_tester/
│ ├── privesc/ # 권한 상승
│ ├── vuln_scanner/
│ ├── exploit_chain/ # 멀티-스텝 공격 체인
│ ├── poc_validator/ # 비파괴 PoC 실행
│ ├── detection/ # Sigma/SPL/KQL 룰 생성
│ ├── llm_redteam/ # OWASP LLM Top 10
│ ├── social_engineer/ # phishing corpus
│ ├── report/ # 최종 보고서 (Jinja2 템플릿)
│ └── selection/ # 에이전트 라우팅
│
├── tools/ # 200+ 도구 래퍼
│ ├── registry.py # ToolRegistry (1,578 줄)
│ ├── network/ # nmap, masscan, ...
│ ├── web/ # sqlmap, ffuf, ...
│ ├── osint/, cloud/, binary/, password/
│ ├── wordlists/ # 번들 폴백 단어사전
│ └── plugin_loader.py # 외부 MCP 서버 합치기
│
├── playbooks/builtin/ # 3 개 기본 플레이북 (.yaml)
│ ├── external-recon.yaml
│ ├── web-app-quick.yaml
│ ├── llm-app-redteam.yaml
│ └── ...
│
├── config/ # 기본 설정 (pentest-ai.yaml)
├── benchmarks/ # 재현 가능 벤치마크 하니스
│ ├── challenges/ # 합법 타깃 정의 (Juice Shop 등)
│ ├── scripts/run_all.sh
│ └── results/2026-05-12/juice-shop/ # raw 출력 보관
│
├── docs/ # 사용자 문서
│ ├── benchmarks/juice-shop.md
│ ├── ci-cd.md
│ ├── credentialed-scans.md
│ └── ROADMAP.md
│
├── tests/ # 1,000+ pytest (Python 3.10–3.13)
│ └── honeypot/ # 자체 honeypot 회귀 테스트 (10/10 강제)
│
├── pyproject.toml # 의존성 + 도구 설정
├── Dockerfile # multi-stage (prod / dev)
├── docker-compose.yml
├── AGENTS.md # AI 코딩 에이전트용 기여 가이드
├── SECURITY.md # 취약점 공개 정책
├── DISCLAIMER.md # AUP 동의 텍스트
└── CHANGELOG.md # 42KB, 릴리즈별 상세 기록
두 가지 주목 포인트.
agents/ 는 "무엇을 할지 결정하는 사람", tools/ 는 "그 사람이 손에 쥐는 무기". 같은 nmap 도 recon-agent 가 호출하면 정찰용 인자가, ad-agent 가 호출하면 SMB 포트 집중용 인자가 들어간다. 도구 자체는 1 개만 등록되어 있고 에이전트가 컨텍스트에 맞게 빌드한다.
"juice-shop 점수만 자랑하지 않겠다"는 의지. 자체 작성한 honeypot 앱에 자체 작성한 버그 10 개를 심어 두고 CI 에서 "10/10 잡혀야 PR 머지 가능" 으로 강제한다. juice-shop 은 너무 유명해서 LLM·프로브 모두 학습돼 있는데, honeypot 점수는 큐레이션된 프로브 라이브러리의 실제 커버리지를 노이즈 없이 측정한다.
이 레포에서 한 가지씩 떼어 가져갈 것.
mcp_server/server.py 의 @mcp.tool() 데코레이터 한 줄이면 보통 함수가 LLM 이 호출할 수 있는 도구가 된다. 인자는 Pydantic 으로 자동 검증된다. 배울 것: MCP 서버를 처음 만들 때 이 패턴이 가장 직관적이다. 인자 타입 힌트가 그대로 JSON-RPC 스키마가 된다.
cli/main.py 는 2,788 줄짜리 단일 파일에 ptai start, ptai mcp, ptai setup, ptai playbook, ptai resume, ptai auth, ptai serve, ptai menu 등 50+ 명령을 담아낸다. 배울 것: Typer 가 click 기반으로 어떻게 깊은 하위 명령 트리를 만드는지, B008 ("function call as default") 가 왜 Typer 에서는 컨벤션인지.
SQLite + 비동기 = 가벼우면서 단일 사용자 환경에 충분. 하지만 워커 스레드가 이벤트 루프보다 오래 사는 미묘한 문제(테스트에서 PytestUnhandledThreadExceptionWarning) 가 README 의 pytest 설정에서 직접 언급된다. 배울 것: 비동기 SQLite 쓸 때 흔히 마주치는 함정과 그 우회법.
Kerberoasting, AS-REP roasting, DCSync, NTLM relay 같은 Windows AD 공격 기법이 모두 impacket 라이브러리에 들어 있다. agents/ad/ad_agent.py 에서 호출 패턴을 볼 수 있다. 배울 것: 보안 학습 관점에서, AD 가 무엇이고 왜 이 공격들이 가능한지 코드를 읽으며 익힐 수 있다.
리액트·뷰처럼 자바스크립트로 렌더하는 SPA 는 단순 HTTP GET 만으로는 라우트·XHR 호출이 안 보인다. BrowserAgent 가 헤드리스 크롬으로 진짜 페이지를 띄워 DOM·네트워크·콘솔까지 캡쳐한다. 배울 것: 크롤러 만들 때 언제 HTTP만으로 충분하고 언제 Playwright/Puppeteer 가 필요한지.
playbooks/builtin/external-recon.yaml 처럼 phase·depends_on·condition·tools 만으로 메서드론을 표현한다. 배울 것: 비슷한 패턴 — GitHub Actions workflow, Ansible playbook, dbt project — 모두 같은 디자인이다. 도메인 전문가가 코드 안 건드리고 워크플로를 정의하게 만드는 표준 패턴.
engine/tracing.py 가 LLM 호출 + 도구 실행을 trace span 으로 자동 기록. Phoenix 같은 LLM 관측 도구에 OTLP 로 보내면 어떤 프롬프트가 어떤 도구를 부르고 토큰을 얼마나 썼는지 시각화된다. 배울 것: AI 에이전트를 디버깅하려면 trace 가 필수. 처음부터 OpenTelemetry 표준으로 가는 게 정답.
SARIF(Static Analysis Results Interchange Format) 는 보안 도구가 결과를 GitHub Code Scanning 으로 보낼 때 쓰는 표준 JSON. engine/sarif.py 가 findings DB 의 데이터를 그대로 SARIF 로 변환한다. 배울 것: 보안 도구 만들 때 사람이 읽을 보고서 + 기계가 읽을 SARIF 두 출력을 모두 내는 게 업계 표준.
특정 LLM 벤더에 묶이지 않으려면 LiteLLM 어댑터 한 겹. OpenRouter, Bedrock, Vertex AI, Ollama 같은 다양한 백엔드를 같은 인터페이스로 호출. 배울 것: 자신의 AI 프로젝트에 LLM 호출 한 줄을 추가할 때 처음부터 LiteLLM 으로 시작하면 나중에 모델 갈아탈 때 코드 안 바꾼다.
실제로 돌리려면 뭐가 필요한가.
다행히 가볍다. 코어 자체는 Python 만 있으면 되고, 무거운 건 외부 보안 도구 쪽이다.
masscan 등 raw socket 쓰는 도구는 root/sudo 필요. 대부분 도구는 일반 사용자로 충분.ANTHROPIC_API_KEY, OPENAI_API_KEY, 또는 로컬 Ollama 중 하나.PTAI_PRICE_LIMIT=25 같은 env 로 조정.난이도별 5 개. 합법 타깃에서만 시도할 것.
pentest-ai 는 실제 공격 행위를 수행한다. 외부 시스템을 허락 없이 스캔하면 한국 정보통신망법, 미국 CFAA(Computer Fraud and Abuse Act), EU GDPR 32 조 등에 의해 형사 처벌 대상이다. 실습용으로는 자기 노트북에 띄운 OWASP Juice Shop, DVWA, HackTheBox, TryHackMe 같은 허락된 환경만 쓸 것.
Juice Shop 은 일부러 취약하게 만든 학습용 웹 앱. docker run -d -p 3000:3000 bkimminich/juice-shop 으로 띄우고 ptai start http://localhost:3000. 17 개 critical, 7 개 attack chain 이 나오는지, 보고서가 어떻게 생겼는지 직접 확인. CHANGELOG 의 0.15.1 항목과 본인 결과를 비교.
claude mcp add pentest-ai -- ptai mcp 한 줄로 등록. Claude Code 를 재시작하고 "내 로컬 Juice Shop 인스턴스(http://localhost:3000)에 대해 인증된 펜테스트 돌려 줘. 결과를 마크다운 보고서로 정리해 줘" 라고 자연어로 시켜 본다. LLM 이 어떤 MCP 도구를 어떤 순서로 부르는지 관찰.
playbooks/builtin/web-app-quick.yaml 를 카피해서 my-api-pentest.yaml 로 변경. phases 에 surface-check(헤더 점검) → api-discovery(OpenAPI 스펙 찾기) → auth-probe(JWT 무효 알고리즘 시도) → rate-limit-test 4 단계를 정의하고 ptai playbook run ./my-api-pentest.yaml. 본인 REST API(자기 소유) 에 돌려 본다.
아직 wrap 되지 않은 보안 도구(예: katana, httpx-toolkit) 를 골라서 tools/registry.py 에 SecurityTool 인스턴스 추가. build_args(인자 빌더) 와 parse_output(결과 파서) 만 짜면 된다. tests/test_tool_X.py 에 단위 테스트 추가하고 PR 보내기. AGENTS.md 의 "Definition of done" 체크리스트를 모두 통과해야 함.
본인 사이드 프로젝트에 staging 환경을 띄우고, .github/workflows/security.yml 에 README 예시처럼 ptai 를 워크플로로 추가. --fail-on high 로 게이팅하고 SARIF 출력을 GitHub Code Scanning 에 업로드. Pull Request 코멘트로 finding 이 자동으로 달리는 걸 확인. 난도가 높은 이유 — staging 환경 + 인증 자격 증명 + 비밀 관리(GitHub Secrets) 까지 손봐야 한다.
8 주 코스로 보면.
SQL Injection, XSS, CSRF, SSRF, XXE, Broken Auth, Sensitive Data Exposure, Misconfig, Outdated Components, Insufficient Logging. Juice Shop 가이드북(OWASP 공식, 무료) 을 따라 하나씩 직접 익스플로잇해 본다. 이론만 보지 말고 손으로 명령어를 친다.
모든 웹 공격은 HTTP 한 줄 한 줄에서 일어난다. Burp Suite Community 로 본인 트래픽을 가로채 보고 헤더·바디·쿠키·세션 토큰의 흐름을 눈으로 본다. 그 다음 sqlmap, ffuf, nuclei 같은 명령형 도구로 같은 일을 자동화해 본다.
pentest-ai 의 모든 코드는 비동기 파이썬. async def, await, asyncio.gather, TaskGroup 사용 패턴을 익힌다. Pydantic v2 모델로 LLM JSON 출력을 검증하는 패턴(response_model) 도. 이게 익숙해지면 어떤 LLM 도구도 만들 수 있다.
modelcontextprotocol.io 의 공식 사양을 읽고 FastMCP 로 본인 도메인의 도구를 노출하는 MCP 서버를 만들어 본다. 예: "내 노션 워크스페이스 조회 도구", "내 GitHub 이슈 검색 도구". pentest-ai/mcp_server/server.py 를 코드 참고로.
Windows AD 가 회사망의 사실상 표준이라 펜테스트는 거의 다 AD 로 귀결된다. TryHackMe 의 "Attacking Kerberos" 룸 + impacket README 의 GetUserSPNs.py, GetNPUsers.py, secretsdump.py 사용법. 가상 머신으로 AD 도메인 컨트롤러를 띄우고 본인 도메인을 공격해 본다.
flaws.cloud 와 flaws2.cloud (무료 학습 환경) 를 단계별로 풀면서 S3 misconfig, IAM 권한 escalation, Lambda 환경 변수 노출, EC2 Metadata Service 공격을 손으로 익힌다. 그 다음 ptai 의 cloud agent + prowler/scout-suite 가 같은 패턴을 어떻게 자동화하는지 코드를 본다.
공격뿐 아니라 방어도 익혀야 한다. agents/detection/ 의 룰 생성 로직을 읽고 Sigma 명세서를 본 다음 자신의 EDR/SIEM 데이터(Splunk/Sentinel/Elastic free tier) 에 룰을 직접 배포해 본다. "공격하면 어떻게 로그가 남고, 그걸 어떻게 잡는가" 의 양면을 모두 봐야 진짜 보안 전문가다.
학습이 진심이면 자격증으로 객관 측정. OSCP(가장 유명, 24시간 실기), PNPT(현실적인 코스, AD 중심), CRTP(AD 만 깊게). pentest-ai 는 이런 자격증 학습의 보조 도구로 쓰면 좋다 — "이 명령어 왜 이렇게 짜는 거지?" 의 답을 코드에서 찾을 수 있어서.
레포 곳곳에 나오는 약자·전문 용어 정리.
engine/cvss.py 가 자동 계산.impacket-GetUserSPNs 명령 한 줄.Ctrl+C 두 번이 pentest-ai 의 HITL 진입점.~/.pentest-ai/aup-consent.txt 에 기록. 위반 시 책임은 사용자에게.더 깊이 파고들 때 직접 열어 볼 1차 출처와 핵심 기술 문서.
pip install ptai 의 배포처. 릴리즈별 버전과 의존성 확인.@mcp.tool() 데코레이터로 MCP 서버를 짜는 프레임워크 가이드(학습 포인트 1의 기술).claude mcp add pentest-ai -- ptai mcp 한 줄. 자연어로 "내 로컬 staging 환경 점검해 줘" 시켜 보고 LLM 이 어떤 도구를 어떤 순서로 부르는지 관찰. API 키 없이 시작 가능.engine/orchestrator.py + 한 에이전트(예: agents/web/web_agent.py) 만 정독. 비동기 + LLM + 외부 도구 호출의 결합 패턴이 모든 AI 에이전트의 공통이다.tools/registry.py 의 BLOCKED_ARG_KEYS + 정규식 인자 검증 패턴을 그대로 가져다 쓴다. 프롬프트 인젝션이 셸 인젝션으로 번지는 흔한 경로를 차단하는 표준 방어법.engine/sarif.py 가 100 줄 안에 변환 로직을 보여 준다.benchmarks/ 처럼 raw 출력 + 스크립트 + 결과 마크다운을 git 에 함께 커밋. "98.7% 정확도" 같은 검증 불가 마케팅 대신 "n=1 single-shot, methodology 여기" 의 정직한 형식이 신뢰를 만든다.