flowchart TB
T([in-scope target]) --> NMAP[nmap<br/>ports + services]
T --> AMASS[amass / subfinder<br/>subdomain enum]
NMAP --> HTTPX[httpx<br/>probe + tech fingerprint]
AMASS --> HTTPX
HTTPX --> NUCLEI[nuclei<br/>template-based scan]
HTTPX --> FFUF[ffuf<br/>content + param fuzzing]
HTTPX --> PW[Playwright<br/>stateful validation]
NUCLEI --> CVE[CVE enrichment<br/>CVSS + EPSS + KEV]
FFUF --> CVE
PW --> CVE
CVE --> EVIDENCE[(Structured Evidence Chain<br/>timestamp + scope + repro + severity)]
style NMAP fill:#0d1b2a,stroke:#5eead4,color:#5eead4
style EVIDENCE fill:#1a1015,stroke:#5eead4,color:#e4e4e8
style CVE fill:#0d1b2a,stroke:#5eead4,color:#5eead4
Reading: The seven tools form a pipeline that maps to the Course 2A S01 offensive state machine. Recon (nmap, amass) builds the attack surface. Probing (httpx) filters and fingerprints. Scanning/fuzzing (nuclei, ffuf) and validation (Playwright) produce candidate findings. CVE enrichment triages them. The evidence chain is the output: everything timestamped, scope-tagged, and reproducible. Each arrow is a scope-validated, schema-first wrapper.
flowchart LR
AGENT[agent emits<br/>tool_use: nuclei<br/>templates: CVE, target: host] --> SCHEMA{schema validate<br/>name + input_schema}
SCHEMA -->|invalid| REJECT[reject + error]
SCHEMA -->|valid| SCOPE{scope validator<br/>host in-scope?<br/>resolved-IP check}
SCOPE -->|no| BLOCK[block + log<br/>legal-exposure prevention]
SCOPE -->|yes| RATE{rate budget ok?}
RATE -->|no| QUEUE[queue / throttle]
RATE -->|yes| EXEC[execute nuclei<br/>-json output]
EXEC --> NORMALIZE[normalize JSON<br/>→ structured findings]
NORMALIZE --> TAG[tag untrusted<br/>scope tag + timestamp]
TAG --> RETURN[return to agent]
style SCOPE fill:#2a0d0d,stroke:#5eead4,color:#f08080
style NORMALIZE fill:#0d1b2a,stroke:#5eead4,color:#5eead4
style TAG fill:#0d1b2a,stroke:#5eead4,color:#5eead4
Reading: Every tool is wrapped the same way. The agent calls a JSON schema (not freeform shell). The wrapper validates the schema, checks scope (the red legal control — resolved-IP, not just hostname), checks the rate budget (DoS prevention), executes, normalizes the output to structured findings, tags them untrusted and scope-tagged, and returns. This is the Course 1 Module 2 schema-first pattern with the security-specific additions (scope, rate, untrusted tag) that make it an offensive harness tool.
flowchart TB
SCAN[nuclei / ffuf<br/>candidate findings] --> VAL{validation layer}
VAL -->|stateless FP| PLAY1[Playwright check<br/>DOM does not confirm]
PLAY1 --> DROP[drop: false positive]
VAL -->|stateful TP| PLAY2[Playwright check<br/>DOM confirms vuln]
PLAY2 --> CVE[CVE enrichment<br/>CVSS + EPSS + KEV]
CVE --> SEV{severity + exploitability}
SEV -->|low EPSS, not in KEV| LOW[low priority finding]
SEV -->|high EPSS or in KEV| HIGH[high priority finding<br/>→ evidence chain]
style DROP fill:#2a0d0d,stroke:#5eead4,color:#f08080
style HIGH fill:#0d1b2a,stroke:#5eead4,color:#5eead4
Reading: nuclei and ffuf produce candidate findings, many of which are stateless false positives. Playwright (stateful, DOM-aware) confirms whether the finding is real — this is the signal-vs-noise filter. CVE enrichment then triages confirmed findings: high EPSS or CISA KEV listing means actively exploitable and urgent. Without the validation layer, the agent drowns in low-quality findings; without enrichment, it cannot prioritize. Both are required for submittable output.
flowchart LR
subgraph EVIDENCE["Structured Evidence Chain (per finding)"]
T1[timestamp<br/>when observed]
T2[scope tag<br/>which in-scope host]
T3[tool + parameters<br/>reproducibility]
T4[raw output<br/>+ normalized finding]
T5[severity<br/>CVSS + EPSS + KEV]
end
EVIDENCE --> SUBMIT([submittable to bug bounty program])
style EVIDENCE fill:#0d1b2a,stroke:#5eead4,color:#e4e4e8
style SUBMIT fill:#1a1015,stroke:#5eead4,color:#5eead4
Reading: A bug bounty program can reject a finding without repro steps. The evidence chain is the repro: timestamp (when), scope tag (where), tool + parameters (how to reproduce), raw + normalized output (what was found), and severity (how bad). This structure is what makes the output submittable — and what distinguishes a bug bounty harness from a pile of scan scripts. Every tool wrapper contributes to this chain; the chain is the harness's product.
# Diagrams — SDD-03: The Bug Bounty Reference Stack
---
## Diagram 1 — The Stack as a Pipeline (Recon to Evidence)
```mermaid
flowchart TB
T([in-scope target]) --> NMAP[nmap<br/>ports + services]
T --> AMASS[amass / subfinder<br/>subdomain enum]
NMAP --> HTTPX[httpx<br/>probe + tech fingerprint]
AMASS --> HTTPX
HTTPX --> NUCLEI[nuclei<br/>template-based scan]
HTTPX --> FFUF[ffuf<br/>content + param fuzzing]
HTTPX --> PW[Playwright<br/>stateful validation]
NUCLEI --> CVE[CVE enrichment<br/>CVSS + EPSS + KEV]
FFUF --> CVE
PW --> CVE
CVE --> EVIDENCE[(Structured Evidence Chain<br/>timestamp + scope + repro + severity)]
style NMAP fill:#0d1b2a,stroke:#5eead4,color:#5eead4
style EVIDENCE fill:#1a1015,stroke:#5eead4,color:#e4e4e8
style CVE fill:#0d1b2a,stroke:#5eead4,color:#5eead4
```
**Reading**: The seven tools form a pipeline that maps to the Course 2A S01 offensive state machine. Recon (nmap, amass) builds the attack surface. Probing (httpx) filters and fingerprints. Scanning/fuzzing (nuclei, ffuf) and validation (Playwright) produce candidate findings. CVE enrichment triages them. The evidence chain is the output: everything timestamped, scope-tagged, and reproducible. Each arrow is a scope-validated, schema-first wrapper.
---
## Diagram 2 — The Schema-First Wrapper Pattern
```mermaid
flowchart LR
AGENT[agent emits<br/>tool_use: nuclei<br/>templates: CVE, target: host] --> SCHEMA{schema validate<br/>name + input_schema}
SCHEMA -->|invalid| REJECT[reject + error]
SCHEMA -->|valid| SCOPE{scope validator<br/>host in-scope?<br/>resolved-IP check}
SCOPE -->|no| BLOCK[block + log<br/>legal-exposure prevention]
SCOPE -->|yes| RATE{rate budget ok?}
RATE -->|no| QUEUE[queue / throttle]
RATE -->|yes| EXEC[execute nuclei<br/>-json output]
EXEC --> NORMALIZE[normalize JSON<br/>→ structured findings]
NORMALIZE --> TAG[tag untrusted<br/>scope tag + timestamp]
TAG --> RETURN[return to agent]
style SCOPE fill:#2a0d0d,stroke:#5eead4,color:#f08080
style NORMALIZE fill:#0d1b2a,stroke:#5eead4,color:#5eead4
style TAG fill:#0d1b2a,stroke:#5eead4,color:#5eead4
```
**Reading**: Every tool is wrapped the same way. The agent calls a JSON schema (not freeform shell). The wrapper validates the schema, checks scope (the red legal control — resolved-IP, not just hostname), checks the rate budget (DoS prevention), executes, normalizes the output to structured findings, tags them untrusted and scope-tagged, and returns. This is the Course 1 Module 2 schema-first pattern with the security-specific additions (scope, rate, untrusted tag) that make it an offensive harness tool.
---
## Diagram 3 — The Validation Layer (Signal vs Noise)
```mermaid
flowchart TB
SCAN[nuclei / ffuf<br/>candidate findings] --> VAL{validation layer}
VAL -->|stateless FP| PLAY1[Playwright check<br/>DOM does not confirm]
PLAY1 --> DROP[drop: false positive]
VAL -->|stateful TP| PLAY2[Playwright check<br/>DOM confirms vuln]
PLAY2 --> CVE[CVE enrichment<br/>CVSS + EPSS + KEV]
CVE --> SEV{severity + exploitability}
SEV -->|low EPSS, not in KEV| LOW[low priority finding]
SEV -->|high EPSS or in KEV| HIGH[high priority finding<br/>→ evidence chain]
style DROP fill:#2a0d0d,stroke:#5eead4,color:#f08080
style HIGH fill:#0d1b2a,stroke:#5eead4,color:#5eead4
```
**Reading**: nuclei and ffuf produce candidate findings, many of which are stateless false positives. Playwright (stateful, DOM-aware) confirms whether the finding is real — this is the signal-vs-noise filter. CVE enrichment then triages confirmed findings: high EPSS or CISA KEV listing means actively exploitable and urgent. Without the validation layer, the agent drowns in low-quality findings; without enrichment, it cannot prioritize. Both are required for submittable output.
---
## Diagram 4 — The Evidence Chain Structure
```mermaid
flowchart LR
subgraph EVIDENCE["Structured Evidence Chain (per finding)"]
T1[timestamp<br/>when observed]
T2[scope tag<br/>which in-scope host]
T3[tool + parameters<br/>reproducibility]
T4[raw output<br/>+ normalized finding]
T5[severity<br/>CVSS + EPSS + KEV]
end
EVIDENCE --> SUBMIT([submittable to bug bounty program])
style EVIDENCE fill:#0d1b2a,stroke:#5eead4,color:#e4e4e8
style SUBMIT fill:#1a1015,stroke:#5eead4,color:#5eead4
```
**Reading**: A bug bounty program can reject a finding without repro steps. The evidence chain is the repro: timestamp (when), scope tag (where), tool + parameters (how to reproduce), raw + normalized output (what was found), and severity (how bad). This structure is what makes the output submittable — and what distinguishes a bug bounty harness from a pile of scan scripts. Every tool wrapper contributes to this chain; the chain is the harness's product.