Skip to main content

S2N-Agent

LLM-powered decision layer for the S2N web vulnerability scanner

S2N 웹 취약점 스캐너를 위한 LLM 의사결정 레이어


개요 / Overview

[한국어]

S2N-Agent는 S2N 스캐너의 플러그인 선택·페이로드 계획·결과 해석을 LLM이 담당하도록 설계된 AI 레이어입니다. 기존 결정론적 스캔 파이프라인에 최소한의 변경으로 통합되며, Ollama(로컬)·HuggingFace(로컬 추론)· Anthropic·OpenAI 중 사용자가 명시적으로 선택한 provider의 LLM으로 동작합니다 — 파인튜닝된 모델은 필요하지 않습니다.

기존: URL/DOM → 조건 충족 → Plugin 실행
목표: URL/DOM/SiteMap/응답 → S2N-Agent 추론 → Plugin 선택 + Payload 계획 → 결과 해석

[English]

S2N-Agent is an AI layer that delegates plugin selection, payload planning, and result interpretation to an LLM. It integrates with the existing S2N scanner pipeline with minimal changes and runs on whichever provider you explicitly select — Ollama (local), HuggingFace (local inference), Anthropic, or OpenAI. No fine-tuned model is required.

Before: URL/DOM → rule match → Plugin execution
After:  URL/DOM/SiteMap/response → S2N-Agent reasoning → Plugin selection + Payload plan → Result interpretation

아키텍처: LLM은 어떻게 연동되는가 / Architecture: How the LLM Connects

[한국어]

에이전트는 provider 중립적으로 설계되어 있습니다. LLMClient 프로토콜(s2nagent/client/base.py) 뒤에 provider를 자유롭게 꽂아 넣는 구조이고, build_client()(s2nagent/client/factory.py)가 사용자가 명시적으로 선택한 provider의 클라이언트를 생성합니다 — 학습이나 배포 없이 바로 사용 가능합니다:

Provider 무엇이 필요한가
ollama 로컬 Ollama 서버 + 아무 모델 태그
huggingface 로컬 GPU/MPS/CPU 추론
anthropic ANTHROPIC_API_KEY (또는 --ai-api-key)
openai OPENAI_API_KEY 또는 OpenAI 호환 로컬 서버 base_url

provider는 반드시 명시해야 합니다 — 인자(--provider/ai_provider/provider) 또는 S2NAGENT_PROVIDER 환경변수 중 하나로 지정하지 않으면 Ollama나 HuggingFace로 자동 선택되지 않고 사용 가능한 provider 목록을 담은 오류로 즉시 종료됩니다. 에이전트를 실제로 동작시키는 데 필요한 최소 요건은 위 표의 provider 중 하나(로컬이든 API든)와 그 provider를 명시적으로 선택하는 것뿐입니다.

[English]

The agent is provider-neutral by design. Providers plug in behind the LLMClient protocol (s2nagent/client/base.py), and build_client() (s2nagent/client/factory.py) constructs whichever provider you explicitly select — no training or deployment required:

Provider What you need
ollama A local Ollama server + any model tag
huggingface Local GPU/MPS/CPU inference
anthropic ANTHROPIC_API_KEY (or --ai-api-key)
openai OPENAI_API_KEY, or an OpenAI-compatible local server base_url

Provider selection is mandatory — specify it via an argument (--provider/ai_provider/ provider) or the S2NAGENT_PROVIDER environment variable. Omitting both raises a clear error listing the available providers instead of silently picking Ollama or HuggingFace. The minimum to actually run the agent is one provider from the table above, explicitly chosen.


AI 모드 / AI Modes

Mode 동작 Behavior
off AI 없음, 기존 S2N 그대로 Vanilla S2N, no AI
assist AI 권고만 로그 출력, 실행은 기존 방식 AI recommendations in log only, execution unchanged
smart 후보/payload 계획을 세우지만 실행 플러그인 목록은 변경하지 않음(실행 제어 미구현) Plans candidates/payloads but does not change which plugins execute (execution control not yet implemented)
aggressive confirmed finding마다 후속 payload를 로그로만 제안 — 공격 체인을 실행하지 않음 Logs suggested follow-up payloads per confirmed finding — does not execute an attack chain

설치 / Installation

현재 상태: S2N-Agent는 PyPI에 배포되어 pip install s2n-agent로 설치할 수 있습니다. 다만 S2N(스캐너)은 ai extra가 포함된 버전이 아직 배포되지 않았으므로 pip install s2n[ai]는 아직 동작하지 않습니다 — S2N 쪽은 아래 안내대로 dev 브랜치를 사용하세요.

Current status: S2N-Agent is published to PyPI (pip install s2n-agent). S2N itself has not shipped a release containing the ai extra yet, so pip install s2n[ai] does not work yet — use S2N's dev branch as described below.

요구사항 / Requirements

  • Python 3.10+
  • S2N — 현재 dev 브랜치에 --ai-mode CLI 옵션이 포함되어 있습니다 (아직 정식 릴리스 태그 없음, 현재 pyproject.toml 버전은 0.3.2). S2N-Agent와 나란히 code-projects/(또는 원하는 부모 디렉터리)에 clone해두세요.
  • LLM provider 하나를 선택해 준비: Ollama(로컬) 또는 HuggingFace(로컬 추론) 또는 Anthropic/OpenAI API 키. 자동 선택은 없으므로 --ai-provider로 반드시 명시해야 합니다.

S2N-Agent 설치 (PyPI) / Install (PyPI)

S2N을 설치한 환경(venv)에 그대로 설치합니다.

pip install s2n-agent

# HuggingFace 로컬 추론까지 필요하면
pip install "s2n-agent[huggingface]"

S2N-Agent 설치 (로컬 editable) / Install (local editable)

에이전트 자체를 수정하며 개발할 때 사용합니다.

# S2N과 나란히 clone
git clone https://github.com/s2n0n/s2n-agent.git
git clone https://github.com/s2n0n/s2n.git

# S2N 개발 환경(venv)에 S2N-Agent를 editable로 설치
cd s2n
python3 -m venv .venv && source .venv/bin/activate   # 또는 기존 개발 venv 사용
pip install -e ../s2n-agent

# HuggingFace 로컬 추론까지 필요하면
pip install -e "../s2n-agent[huggingface]"

# 개발(테스트) 환경
pip install -e "../s2n-agent[dev]"

설치 확인:

python3 -c "import s2nagent; print('OK')"

ModuleNotFoundError가 아니라 OK가 출력되면 준비 완료입니다 — S2N scan --ai-mode ...가 더 이상 "s2nagent 패키지 미설치" 경고 없이 AI 모드를 활성화합니다.


S2N 통합 / S2N Integration

S2N dev 브랜치에 --ai-mode/--ai-model/--ai-endpoint/--ai-provider/--ai-api-key CLI 옵션이 내장되어 있습니다. 아직 정식 릴리스 태그는 없으므로, 위 설치 절차대로 dev 브랜치를 사용하세요.

S2N's dev branch already includes built-in --ai-mode/--ai-model/--ai-endpoint/--ai-provider/--ai-api-key CLI options. There's no tagged release yet, so follow the Installation steps above to use the dev branch.

두 개의 진입점 / Two entry points: S2N에는 이 에이전트를 주입하는 경로가 두 곳입니다 — 둘 다 s2n/s2nscanner/ai_integration.pybuild_ai_plugins() 공용 헬퍼를 거쳐 동일한 S2NAgentPlugin을 동일한 방식으로 인스턴스화하므로, 어느 경로로 들어와도 에이전트 동작은 동일합니다.

  1. CLI — 아래 CLI 사용법 참고.
  2. Chrome 확장 프로그램 — S2N의 fix/on-scan-complete-hook 브랜치(아직 dev 미병합)부터, extension/의 Options 페이지에서 AI 모드/provider/모델/엔드포인트/API 키를 설정하고 Popup의 AI 토글을 켜면 Native Messaging(native_host.py)을 통해 동일한 에이전트가 주입됩니다. Popup 토글은 항상 assist 모드로 고정됩니다(README AI 모드 표 기준 가장 안전한 기본값). CLI 옵션에 없는 필드(예: 구버전 확장 프로그램)는 ai_mode="off"로 안전하게 기본 처리되어 기존 스캔 동작에 영향이 없습니다.

There are two entry points that inject this agent into S2N — both go through the shared build_ai_plugins() helper in s2n/s2nscanner/ai_integration.py, so behavior is identical regardless of which path is used:

  1. CLI — see CLI Usage below.
  2. Chrome extension — as of S2N's fix/on-scan-complete-hook branch (not yet merged to dev), the extension's Options page lets you configure AI mode/provider/model/endpoint/API key, and the Popup's AI toggle (fixed to assist mode, the safest default) wires the same agent in via Native Messaging (native_host.py). Fields absent from older extension clients default safely to ai_mode="off", so existing scans are unaffected.

CLI 사용법 / CLI Usage

# AI 없음 (기존 동작) — provider 지정 불필요
s2n scan -u https://target.com

# assist 모드 — AI 권고를 로그에 출력, 실행은 기존 플러그인 (provider는 반드시 명시)
s2n scan -u https://target.com --ai-mode assist --ai-provider ollama

# smart 모드 — 후보/payload 계획 수립(실행 플러그인 목록은 아직 변경하지 않음)
s2n scan -u https://target.com --ai-mode smart --ai-provider ollama

# aggressive 모드 — confirmed finding마다 후속 payload를 로그로 제안(공격 체인 미실행)
s2n scan -u https://target.com --ai-mode aggressive --ai-provider ollama

# Ollama 모델/엔드포인트를 명시적으로 지정
s2n scan -u https://target.com \
  --ai-mode smart \
  --ai-provider ollama \
  --ai-model s2n-agent \
  --ai-endpoint http://localhost:11434

# Claude / GPT 등 API 기반 provider 사용
s2n scan -u https://target.com --ai-mode smart \
  --ai-provider anthropic --ai-model claude-sonnet-4-5 --ai-api-key "$ANTHROPIC_API_KEY"

s2n scan -u https://target.com --ai-mode smart \
  --ai-provider openai --ai-model gpt-4o-mini --ai-api-key "$OPENAI_API_KEY"

--ai-provider를 생략하면 S2NAGENT_PROVIDER 환경변수를 확인하고, 둘 다 없으면 --ai-modeoff가 아닌 한 명확한 오류로 종료됩니다 — Ollama나 HuggingFace가 자동으로 선택되지 않습니다. --ai-api-key를 생략하면 각 provider가 자체적으로 ANTHROPIC_API_KEY/OPENAI_API_KEY 환경변수를 읽습니다.

참고: S2N CLI의 --ai-provider 자체 기본값은 아직 None입니다 — 이 저장소(s2n-agent)의 provider 필수화는 S2N-Agent 쪽 라이브러리 동작이며, S2N CLI가 넘겨준 ai_provider=None을 그대로 받으면 위와 동일한 오류로 종료됩니다. 즉 --ai-modeoff가 아닌 값으로 쓸 때는 항상 --ai-provider를 함께 지정하세요.

Python API

from s2nagent import S2NAgent

# provider는 반드시 명시해야 한다 — 생략하면 S2NAGENT_PROVIDER 환경변수를 확인하고,
# 둘 다 없으면 ValueError로 즉시 실패한다(Ollama/HuggingFace 자동 선택 없음).
agent = S2NAgent(provider="ollama", mode="smart")

# endpoint/model을 생략하면 선택된 provider 클라이언트 자신의 기본값을 쓴다 —
# 특정 Ollama 서버/모델 태그를 명시하고 싶을 때만 지정
agent = S2NAgent(provider="ollama", endpoint="http://localhost:11434", model="s2n-agent", mode="smart")

# Claude / GPT 등 다른 provider 사용 — endpoint를 생략하면 각 provider의 공식
# 엔드포인트(https://api.anthropic.com, https://api.openai.com/v1)를 쓴다
agent = S2NAgent(provider="anthropic", model="claude-sonnet-4-5", api_key="...")
agent = S2NAgent(provider="openai", model="gpt-4o-mini", api_key="...")
agent = S2NAgent(provider="openai", model="my-local-model",
                  endpoint="http://localhost:8000/v1")  # OpenAI 호환 로컬 서버

# Task A — 플러그인 선택
result = agent.select_plugin(
    url="/search?q=test",
    dom="<input name='q' type='text'>",
    sitemap_summary="3 forms, 0 file inputs",
)
# {"plugin": "xss", "confidence": 91, "reason": "input[name=q] detected"}

# Task B — 페이로드 계획
payloads = agent.plan_payloads(plugin="xss", parameter="q", context="html_body")
# {"payloads": ["<svg/onload=alert(1)>", ...], "strategy": "..."}

# Task C — FP 필터
verdict = agent.filter_false_positive(
    finding="Possible XSS",
    evidence="<script>alert(1)</script>",
    response_body="<script>alert(1)</script> reflected",
)
# {"verdict": "confirmed", "confidence": 95, "reason": "..."}

# Task D — 다음 액션 계획
plan = agent.plan_next_action(
    completed=["xss", "csrf"],
    findings=[{"plugin": "jwt", "severity": "HIGH"}],
    sitemap="admin route /admin/panel discovered",
)
# {"next_action": "path_traversal", "priority": "high", "reason": "..."}

# on_finding 콜백 (Scanner 실시간 피드백)
from s2n.s2nscanner.scan_engine import Scanner
scanner = Scanner(config=config, on_finding=agent.analyze_finding)

Plugin Agent Registry

각 S2N 플러그인은 전담 PluginAgent를 가질 수 있습니다. xss/sqlinjection/jwt/file_upload(P0, 가장 정교한 전담 판정 로직)와 csrf/oscommand/path_traversal/sensitive_files/brute_force/soft_brute_force/autobot (P1/P2, prompt profile 기반) 총 11개가 구현되어 있습니다. 모든 PluginAgent는 provider 선택과 무관하게 동일한 LLMClient를 공유합니다 — registry.py에 선언된 adapter/fallback_model 필드는 현재 메타데이터일 뿐 런타임 model 라우팅에는 쓰이지 않습니다. react2shell은 아직 registry에 class: None으로 남아있습니다 — 대응하는 S2N 플러그인 자체가 없는 상태(docs/plugins/react2shell.md)라 항상 should_run=False로 안전하게 no-op 처리됩니다.

from s2nagent.plugin_agents import get_plugin_agent
from s2nagent.client import build_client

client = build_client(provider="anthropic", model="claude-sonnet-4-5", api_key="...")

agent = get_plugin_agent("brute_force", client)  # None이면 미구현 플러그인
decision = agent.evaluate_target(
    url="https://target.com/login",
    dom="<form><input type='password' name='pass'></form>",
    sitemap_summary="login form, no CAPTCHA observed",
)
# {"should_run": True, "confidence": 85, "reason": "...", "context": {"risk_signals": {...}}, ...}

각 에이전트는 LLM이 페이로드/판정을 "제안"하고, 파이썬 코드가 그 제안이 안전 범위를 벗어나지 않는지 결정론적으로 검증하는 구조를 공유합니다 — 예를 들어 재정렬 계열 메서드(plan_payload_order 등)는 LLM이 반환한 목록이 원래 후보 집합의 순열이 아니면 항상 원본 순서로 폴백하고, brute_force/autobot은 잠금정책·CAPTCHA· WAF 챌린지가 감지되면 confidence와 무관하게 should_run을 강제로 False로 둡니다. 자세한 설계는 docs/plugins/*.mddocs/superpowers/specs/2026-08-02-p1-p2-plugin-agents-design.md를 참고하세요.


모델 학습·배포 (실험적) / Model Training & Deployment (Experimental)

[한국어] 에이전트를 실행하는 데 파인튜닝된 모델은 필요하지 않습니다 — 위 아키텍처 섹션의 provider 중 하나만 명시적으로 선택하면 바로 동작합니다.

scripts/train.py/evaluate.py/deploy_ollama.sh, configs/lora_*.yaml, data/*.jsonl, s2nagent/models/Modelfile은 XSS PluginAgent 판정 정확도를 높이려는 선택적 실험 자산입니다. 현재 다음 사유로 에이전트의 핵심 실행 경로에는 연결되어 있지 않습니다:

  • plugin_agents/registry.pyadapter/fallback_model 필드가 런타임 model 라우팅에 쓰이지 않음 (모든 PluginAgent가 provider 선택과 무관하게 동일한 client를 공유).
  • 학습 파이프라인이 두 갈래(scripts/train.py의 MLX 기반과 scripts/plugin_agents/train_xss_lora_peft.py의 HF PEFT 기반)로 나뉘어 있고, deploy_ollama.sh가 기대하는 MLX .npz adapter 포맷과 현재 커밋된 adapter(adapters/*/adapter_model.safetensors, HF PEFT 형식)가 서로 호환되지 않음.
  • 가장 긍정적인 평가 결과(HF+PEFT, +26%p)가 재현 가능한 형태로 커밋되어 있지 않음.

각 스크립트를 직접 실험해보고 싶다면 --help를 참고하세요. 저장소를 정리하는 방향은 docs/agent-development-plan.md §1.2(제외 범위)를 참고하세요.

[English] Fine-tuning is not required to run the agent — any provider from the Architecture section above works out of the box once explicitly selected.

scripts/train.py/evaluate.py/deploy_ollama.sh, configs/lora_*.yaml, data/*.jsonl, and s2nagent/models/Modelfile are optional experiments aimed at improving the XSS PluginAgent's judgment accuracy. They are not wired into the agent's core execution path: the registry's adapter/fallback_model fields aren't used for runtime model routing, the training pipeline is split across two incompatible formats (MLX .npz vs. the committed HF PEFT adapter_model.safetensors), and the most positive evaluation result isn't committed in reproducible form. See each script's --help if you want to experiment, and docs/agent-development-plan.md §1.2 for the scoping rationale.


프로젝트 구조 / Project Structure

s2n-agent/
├── s2nagent/
│   ├── agent.py                  # S2NAgent — 최상위 오케스트레이터
│   ├── cli.py                    # `s2n-agent` 독립 CLI (select/plan/filter/next/deploy/smoke)
│   ├── constants.py               # PLUGINS 목록, AGENT_MIN_CONFIDENCE 등 전역 상수
│   ├── client/
│   │   ├── base.py               # LLMClient Protocol — 모든 provider가 만족해야 하는 계약
│   │   ├── factory.py            # build_client() — provider 명시 필수(ollama/hf/anthropic/openai)
│   │   ├── ollama.py             # Ollama /api/generate 클라이언트
│   │   ├── huggingface.py        # HuggingFace 로컬 추론 (MPS/CUDA/CPU)
│   │   ├── anthropic_client.py   # Claude API 클라이언트
│   │   └── openai_compatible.py  # OpenAI/OpenAI 호환 서버 클라이언트
│   ├── plugin_agents/            # 플러그인별 전담 에이전트 (registry.py가 이름→클래스 매핑)
│   │   ├── base.py                # BasePluginAgent, estimate_os_from_context 등 공유 헬퍼
│   │   ├── registry.py            # get_plugin_agent(name, client) — 11개 구현 + react2shell(class=None)
│   │   ├── xss.py, sqlinjection.py, jwt.py, file_upload.py       # P0 (가장 정교한 전담 로직)
│   │   └── csrf.py, oscommand.py, path_traversal.py,             # P1/P2 (공통 모델 + prompt profile)
│   │       sensitive_files.py, brute_force.py, soft_brute_force.py, autobot.py
│   ├── plugins/
│   │   └── s2n_agent_plugin.py   # S2NAgentPlugin (pre_scan/run/post_scan/cleanup/on_scan_complete)
│   ├── tasks/
│   │   ├── plugin_selection.py   # Task A
│   │   ├── router.py              # 상위 top-k 후보 선정 (pre_scan에서 사용)
│   │   ├── payload_planning.py   # Task B (자유 생성 모드 + 후보 재정렬 모드)
│   │   ├── false_positive.py     # Task C
│   │   └── multi_step.py         # Task D
│   ├── data/
│   │   ├── generator.py          # 학습 데이터 생성기
│   │   └── schemas.py            # ChatML 스키마
│   └── models/
│       └── Modelfile             # Ollama 배포 설정
├── configs/
│   ├── lora_3b.yaml              # Qwen2.5-Coder-3B LoRA 설정
│   └── lora_7b.yaml              # Qwen2.5-Coder-7B LoRA 설정
├── data/
│   ├── train.jsonl               # 학습 데이터 (3,200 samples)
│   ├── valid.jsonl               # 검증 데이터 (400 samples)
│   └── test.jsonl                # 테스트 데이터 (400 samples)
├── docs/
│   ├── plugins/                  # 플러그인별 전담 에이전트 설계서 (16섹션 구조) + integration-gaps.md
│   └── superpowers/               # 이 저장소에서 진행한 spec/plan 문서 아카이브
├── scripts/
│   ├── split_data.py             # train/val/test 분리
│   ├── train.py                  # mlx-lm 학습 래퍼
│   ├── evaluate.py               # 평가 스크립트
│   └── deploy_ollama.sh          # Ollama 배포 자동화
├── tests/                        # pytest — plugin_agents/tasks/registry 전체 커버
└── pyproject.toml

S2N 통합 상세 / S2N Integration Details

S2N 스캐너의 플러그인 생명주기 훅을 활용합니다. CLI(runner.py)와 Chrome 확장 프로그램 (native_host.py) 양쪽 진입점 모두 이 훅 순서를 그대로 따릅니다 — S2NAgentPluginScanner.plugins 리스트의 맨 앞에 놓여 항상 다른 플러그인보다 먼저 실행됩니다.

Hooks into S2N scanner's plugin lifecycle. Both entry points (the CLI's runner.py and the Chrome extension's native_host.py) follow the exact same hook sequence — S2NAgentPlugin is always prepended to Scanner.plugins, so it runs before every other plugin.

Scanner.scan()
  ↓ smart_crawl() → scan_context.sitemap 자동 첨부
  ↓ for plugin in discovered_plugins:
      ↓ plugin.pre_scan(ctx)   ← AI: sitemap 분석, 실행 여부 결정
      ↓ plugin.run(ctx)        ← 실제 스캔
      ↓ plugin.post_scan(ctx)  ← AI: 결과 해석, 다음 액션 계획
      ↓ plugin.cleanup(ctx)
  ↓ for plugin in discovered_plugins:      ← 전체 루프 종료 후 1회
      ↓ plugin.on_scan_complete(ctx, results)  ← AI: aggregate FP 필터 + multi-step planner
  ↓ ScanReport 반환

on_scan_complete는 개별 플러그인이 아니라 스캔 전체 결과를 종합해야 하는 훅이라 루프 밖에서 한 번만 호출됩니다. S2N dev 브랜치에 이 호출부가 배선되어 있습니다 (s2n0n/s2n#154).

각 훅에서 에이전트가 실제로 하는 일 / What the agent actually does at each hook

훅 / Hook 에이전트 역할 / Agent's role 담당 Task
pre_scan RouterTask로 sitemap 기반 top-k 플러그인 후보 선정 → (smart/aggressive) P0 PluginAgent로 후보별 should_run 평가 → 최적 후보에 payload 계획 A (선택), B (페이로드)
run (assist 모드만) 위에서 나온 권고를 로그로만 출력 — 실제 실행은 여전히 기존 플러그인들이 담당
on_finding (실시간 콜백) 각 finding이 리포팅되는 즉시 FP 판정 + (aggressive) confirmed된 항목에 후속 payload 권고 C (FP 필터)
post_scan 에이전트 자신의 PluginResult 반환(집계는 on_scan_complete로 이관)
on_scan_complete (전체 스캔 종료 후 1회) 실시간/일괄 finding 병합 → 최종 FP 필터 → "다음에 뭘 스캔해야 하는가" 계획 → session_data["agent_state"]에 저장 C (집계 FP 필터), D (다음 액션)

즉 에이전트는 스캔 결과를 만들어내는 주체가 아니라, 기존 11개 플러그인을 언제/어떤 순서로 돌릴지 결정하고, 그 결과를 해석해서 다음 액션을 제안하는 의사결정 레이어입니다 — off 모드에서는 이 모든 훅이 즉시 no-op으로 반환되어 기존 S2N과 100% 동일하게 동작합니다.

In other words, the agent doesn't produce scan results itself — it's a decision layer that decides when/in what order to run the existing 11 plugins, and interprets their results to propose the next action. With ai_mode="off", every one of these hooks returns immediately as a no-op, so behavior is identical to vanilla S2N.

수동 통합 / Manual integration (without CLI):

from s2n.s2nscanner.scan_engine import Scanner
from s2n.s2nscanner.interfaces import ScanConfig, ScannerConfig
from s2nagent.plugins.s2n_agent_plugin import S2NAgentPlugin

agent_plugin = S2NAgentPlugin(
    ai_mode="smart",
    ai_provider="ollama",  # 반드시 명시 — 생략하면 ValueError (자동 선택 없음)
    # ai_model/ai_endpoint를 생략하면 선택한 provider의 기본값을 쓴다.
    # ai_provider="anthropic", ai_model="claude-sonnet-4-5", ai_api_key="...",  # Claude/GPT 등 사용 시
)

scanner = Scanner(
    config=ScanConfig(
        target_url="https://target.com",
        scanner_config=ScannerConfig(ai_mode="smart"),
    ),
    plugins=[agent_plugin],
    on_finding=lambda f: print(f"Finding: {f.title}"),
)
report = scanner.scan()

MITRE ATT&CK 매핑 / MITRE ATT&CK Mapping

S2N-Agent가 선택할 수 있는 플러그인과 ATT&CK 매핑. Plugins available for AI selection and their ATT&CK mappings.

Plugin TID Tactic Agent 구현
xss T1059.007 Execution ✅ P0
sqlinjection T1190 Initial Access ✅ P0
jwt T1528 Credential Access ✅ P0
file_upload T1505.003 Persistence ✅ P0
oscommand T1059 Execution ✅ P1
path_traversal T1083 Discovery ✅ P1
sensitive_files T1552.001 Credential Access ✅ P1
csrf T1185 Collection ✅ P2
brute_force T1110 Credential Access ✅ P2
soft_brute_force T1110 Credential Access ✅ P2
autobot T1190 Initial Access ✅ P2
react2shell T1505.003 Persistence ⛔️ 미구현 — 대응하는 S2N 플러그인 없음 (docs/plugins/react2shell.md), registry에서 항상 should_run=False

개발 로드맵 / Development Roadmap

단계 상태 작업
Week 1 ✅ 완료 ScannerConfig AI 필드, CLI 옵션, 패키지 구조, Ollama/HF 클라이언트, Tasks A-D, 4,000 샘플 생성
Week 2 ✅ 완료 train/val/test 분리, LoRA 설정(3B/7B), 학습 스크립트, 평가 스크립트, Ollama 배포 자동화
Week 3 ✅ 완료 on_scan_complete 훅 구현(집계 FP 필터/multi-step planner), SiteMap 통합, P0 4개 에이전트(xss/sqli/jwt/file_upload)
P1/P2 플러그인 에이전트 ✅ 완료 csrf/oscommand/path_traversal/sensitive_files/brute_force/soft_brute_force/autobot 7종 구현 — docs/plugins/*.md 설계 기반, registry 배선 완료
Multi-provider LLM client ✅ 완료 build_client() 팩토리로 Ollama/HuggingFace/Anthropic(Claude)/OpenAI(호환) provider 명시적 선택 지원
S2N 쪽 크로스레포 배선 ✅ 완료 on_scan_complete 호출부 S2N scan_engine.py에 추가 (s2n0n/s2n#154), pyproject.toml build-backend 버그 수정
확장 프로그램 AI 모드 연동 ✅ 완료 S2N fix/on-scan-complete-hook 브랜치(미병합)에 ai_integration.build_ai_plugins() 공용 헬퍼 + native_host.py 배선, Native Messaging 프로토콜에 ai_* 필드 추가, 확장 프로그램 Popup/Options에 AI 토글·설정 UI 추가 — CLI와 동일한 에이전트가 이제 브라우저 확장에서도 동작
플러그인 registry 정합성 ✅ 완료 s2nagent.constants.get_known_plugins()가 s2n 설치 시 실제 discover_plugins()와 대조해 드리프트(react2shell 등)를 1회 경고로 감지
Stage 1: 현재 동작 정합화 ✅ 완료 provider별 기본 endpoint/model 격리(Anthropic/OpenAI가 CLI 포함 어디서도 더 이상 Ollama 주소를 받지 않음), assist 모드가 아무도 쓰지 않던 plugin_recommendation 대신 실제로 채워지는 router_candidates를 읽도록 수정, on_scan_completecompleted_plugins에서 agent 자신 제외 — docs/agent-development-plan.md §12 1단계 완료 조건 충족 (180 tests)
provider 필수 선택 ✅ 완료 build_client()auto(Ollama 우선 탐지 → HuggingFace 폴백) 기본 동작 제거 — provider를 인자 또는 S2NAGENT_PROVIDER 환경변수로 명시하지 않으면 명확한 오류로 종료. CLI --provider choice에서도 auto 제거, S2N CLI를 통한 사용도 이제 --ai-provider 명시 필요
Stage 2–7 (shadow planner, PolicyValidator, 전역 request budget, bounded executor 등) 🔄 예정 실행 제어를 실제로 구현하는 남은 단계 — 설계와 완료 조건은 docs/agent-development-plan.md §5–§12 참고. S2N(스캐너) 저장소 변경이 필요해 별도 계획으로 진행
react2shell ⏳ 보류 S2N 저장소에 대응하는 React SSR/템플릿 인젝션 플러그인 자체가 없음 — registry는 항상 should_run=False로 안전하게 no-op 처리 (docs/plugins/react2shell.md)
P1 LoRA 어댑터 승격 ⏸️ 보류 docs/agent-development-plan.md §1.2에 따라 파인튜닝/adapter 작업은 이번 로드맵 범위에서 제외 — 실행 제어(Stage 2–7)와 end-to-end 벤치마크 완료 후, 재현 가능한 10%p+ 개선이 확인될 때만 재개
학습 데이터셋 확충 ⏸️ 보류 위와 동일한 사유로 보류 — data/·scripts/train.py 등은 실험 자산으로 유지되며 핵심 실행 경로에 연결하지 않음
PyPI 배포 (S2N-Agent) ✅ 완료 v0.1.0 태그 push → GitHub Actions가 Trusted Publishing(OIDC)으로 PyPI 배포 — pip install s2n-agent 가능
PyPI 배포 (S2N 연동) 🔄 예정 S2N PyPI 최신 릴리스(0.3.2)에는 ai extra가 없음 — S2N 쪽 버전 승격·재배포가 있어야 pip install s2n[ai]가 동작. ai extra에 상한(>=0.1.0,<0.2)도 함께 필요
CI AI 모드 통합 테스트 ⏳ 예정 S2N CI에 --ai-mode assist 스모크 테스트 + registry/discover_plugins() 정합성 단위 테스트 추가

라이선스 / License

MIT License. See LICENSE.


주의: 이 도구는 허가된 보안 테스트 및 교육 목적으로만 사용하세요. Warning: This tool is intended for authorized security testing and educational purposes only.

Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

s2n_agent-0.1.0.tar.gz (101.0 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

s2n_agent-0.1.0-py3-none-any.whl (88.2 kB view details)

Uploaded Python 3

File details

Details for the file s2n_agent-0.1.0.tar.gz.

File metadata

  • Download URL: s2n_agent-0.1.0.tar.gz
  • Upload date:
  • Size: 101.0 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for s2n_agent-0.1.0.tar.gz
Algorithm Hash digest
SHA256 eee6f4ab031d8a8b99955879e537322b64beb478467370c680dfb1bac56a1d4b
MD5 8b35db09cb9d8b153dda93c6c0059022
BLAKE2b-256 e11da4358056efab2b392f04706a1f663d6c66c21598a5569d871de4e0cda8e6

See more details on using hashes here.

Provenance

The following attestation bundles were made for s2n_agent-0.1.0.tar.gz:

Publisher: ci-cd.yml on s2n0n/s2n-agent

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

File details

Details for the file s2n_agent-0.1.0-py3-none-any.whl.

File metadata

  • Download URL: s2n_agent-0.1.0-py3-none-any.whl
  • Upload date:
  • Size: 88.2 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? Yes
  • Uploaded via: twine/7.0.0 CPython/3.13.14

File hashes

Hashes for s2n_agent-0.1.0-py3-none-any.whl
Algorithm Hash digest
SHA256 150123826c9cdf919bee5a331b5f2983f0673d36955a030e3d888d6c197be0cf
MD5 4bd5be11936a159adf238b46346af0fd
BLAKE2b-256 e988bce9da959728a3c582d6faf01222c75294fa75d66cf0802c4604a4f03593

See more details on using hashes here.

Provenance

The following attestation bundles were made for s2n_agent-0.1.0-py3-none-any.whl:

Publisher: ci-cd.yml on s2n0n/s2n-agent

Attestations: Values shown here reflect the state when the release was signed and may no longer be current.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Sentry Error logging StatusPage Status page