daemon-sec-cheatsheet

The cheatsheet vault for operators: AD, enumeration, exploitation, priv-esc, web, DFIR
git clone https://git.daemon-sec.xyz/daemon-sec-cheatsheet.git
Log | Files | Refs | README | LICENSE

nuclei.md (24563B)


      1 ---
      2 title: "Nuclei"
      3 description: "Nuclei template-based vulnerability scanning: template selection, tags, severity and workflows."
      4 category: enumeration
      5 tags: [enumeration, scanning, vulnerabilities]
      6 tools: [Nuclei]
      7 difficulty: intermediate
      8 updated: "2026-08-09"
      9 source: "vault:Tools/Nuclei-Cheatsheet.md"
     10 ---
     11 
     12 # Nuclei
     13 
     14 Fast, template-driven vulnerability scanner from ProjectDiscovery (v3.x). Nuclei sends requests defined in community-maintained YAML **templates** and matches responses to confirm vulnerabilities with near-zero false positives. It supports HTTP, DNS, TCP, SSL, WHOIS, headless-browser, JavaScript and code protocols. The typical workflow is a recon pipeline — enumerate subdomains with subfinder, probe live hosts with httpx, then pipe the live URLs into `nuclei`. It clusters similar requests and runs templates in parallel, so it is fast, but that same speed can trip WAFs and rate limits on fragile CTF/lab targets — tune `-rl` and `-c` accordingly.
     15 
     16 > **Important — Version note:**
     17 > 1. Nuclei is in **active development** — flags change between minor releases. Always confirm with `nuclei -h`.
     18 > 2. Requires **Go >= 1.24.2** to build from source.
     19 > 3. This note targets **v3.x**. A few flag names people commonly assume do **not** exist (see Troubleshooting).
     20 
     21 ## Quick-Reference Flag Table
     22 
     23 | Flag (short / long) | Purpose |
     24 |---|---|
     25 | `-u` / `-target` | Target URL(s)/host(s), comma-separated |
     26 | `-l` / `-list` | File of targets, one per line |
     27 | `-im` / `-input-mode` | Input file mode: `list`, `burp`, `jsonl`, `yaml`, `openapi`, `swagger` |
     28 | `-t` / `-templates` | Template file/dir to run |
     29 | `-turl` / `-template-url` | Run template(s) from a URL |
     30 | `-w` / `-workflows` | Run a workflow (ordered template chain) |
     31 | `-et` / `-exclude-templates` | Exclude template file/dir |
     32 | `-tags` / `-etags` | Include / exclude by tag |
     33 | `-itags` / `-include-tags` | Force-run tags even if excluded by default |
     34 | `-s` / `-severity` | Filter by severity: `info,low,medium,high,critical,unknown` |
     35 | `-es` / `-exclude-severity` | Exclude by severity |
     36 | `-a` / `-author` | Filter by template author |
     37 | `-id` / `-eid` | Include / exclude by template ID |
     38 | `-tc` / `-template-condition` | Run templates matching an expression |
     39 | `-as` / `-automatic-scan` | Wappalyzer tech-detection → tag mapping |
     40 | `-nt` / `-new-templates` | Only templates new in latest release |
     41 | `-o` / `-output` | Write findings to file |
     42 | `-j` / `-jsonl` | JSONL output |
     43 | `-je` / `-json-export` | Export results as JSON file |
     44 | `-jle` / `-jsonl-export` | Export results as JSONL file |
     45 | `-se` / `-sarif-export` | Export results as SARIF file |
     46 | `-me` / `-markdown-export` | Export results as Markdown dir |
     47 | `-silent` | Findings only, no banners/logs |
     48 | `-nc` / `-no-color` | Disable ANSI colour |
     49 | `-v` / `-vv` | Verbose / show loaded templates |
     50 | `-debug` | Show all requests + responses |
     51 | `-sresp` / `-store-resp` | Save all req/resp to disk |
     52 | `-rl` / `-rate-limit` | Requests per second (default 150) |
     53 | `-bs` / `-bulk-size` | Hosts analysed in parallel per template (default 25) |
     54 | `-c` / `-concurrency` | Templates run in parallel (default 25) |
     55 | `-timeout` | Per-request timeout seconds (default 10) |
     56 | `-retries` | Retries per failed request (default 1) |
     57 | `-mhe` / `-max-host-error` | Errors before skipping a host (default 30) |
     58 | `-p` / `-proxy` | HTTP/SOCKS5 proxy |
     59 | `-H` / `-header` | Custom header/cookie `key:value` |
     60 | `-sni` | TLS SNI hostname |
     61 | `-i` / `-interface` | Network interface for network scans |
     62 | `-sip` / `-source-ip` | Source IP for network scans |
     63 | `-r` / `-resolvers` | Resolver list file |
     64 | `-sr` / `-system-resolvers` | Use system DNS as fallback |
     65 | `-iserver` / `-itoken` | Self-hosted Interactsh server / token |
     66 | `-ni` / `-no-interactsh` | Disable OAST, skip OAST templates |
     67 | `-sf` / `-secret-file` | Secrets/auth config file |
     68 | `-dast` | Enable DAST (fuzzing) templates |
     69 | `-ft` / `-fuzzing-type` | Override fuzz type: `replace,prefix,postfix,infix` |
     70 | `-fm` / `-fuzzing-mode` | Override fuzz mode: `multiple,single` |
     71 | `-validate` | Validate templates |
     72 | `-up` / `-update` | Update the engine |
     73 | `-ut` / `-update-templates` | Update templates |
     74 | `-headless` | Enable headless-browser templates |
     75 | `-page-timeout` | Seconds to wait per page in headless (default 20) |
     76 
     77 ## Installation
     78 
     79 ```bash
     80 # 1) Go install (needs Go >= 1.24.2) — installs to $GOPATH/bin
     81 go install -v github.com/projectdiscovery/nuclei/v3/cmd/nuclei@latest
     82 
     83 # 2) Homebrew (macOS / Linux)
     84 brew install nuclei
     85 
     86 # 3) Docker
     87 docker pull projectdiscovery/nuclei:latest
     88 docker run --rm projectdiscovery/nuclei:latest -u https://example.com
     89 
     90 # 4) Binary release — download from GitHub releases, unzip, move to PATH
     91 # https://github.com/projectdiscovery/nuclei/releases
     92 unzip nuclei_3.x.x_linux_amd64.zip
     93 sudo mv nuclei /usr/local/bin/
     94 
     95 # Verify
     96 nuclei -version
     97 ```
     98 
     99 > **Install breakdown:**
    100 > 1. **go install** — pulls latest tagged source; keep Go updated or the build fails.
    101 > 2. **brew** — easiest on Kali/macOS; may lag a release behind.
    102 > 3. **docker** — mount a volume for templates/output; the container has no persistent template store by default.
    103 > 4. **binary** — fastest for air-gapped/offline lab boxes; grab the matching arch.
    104 
    105 ## Template Management
    106 
    107 Templates live in **`~/nuclei-templates/`** by default. Override with the `NUCLEI_TEMPLATES_DIR` environment variable or the `-ud` flag. On first run nuclei auto-downloads templates.
    108 
    109 ```bash
    110 # Update the nuclei engine itself
    111 nuclei -up
    112 nuclei -update
    113 
    114 # Update templates to the latest release
    115 nuclei -ut
    116 nuclei -update-templates
    117 
    118 # Install/update templates into a custom directory
    119 nuclei -ut -ud /opt/nuclei-templates
    120 
    121 # Disable the automatic update check (useful in CI / offline labs)
    122 nuclei -u https://target -duc
    123 
    124 # Show installed templates version
    125 nuclei -tv
    126 
    127 # List all templates matching current filters (dry run, no scan)
    128 nuclei -tl -tags cve -severity critical
    129 
    130 # List all available tags
    131 nuclei -tgl
    132 
    133 # Run only templates added in the latest templates release
    134 nuclei -u https://target -nt
    135 
    136 # Reset ALL nuclei config + data (including templates)
    137 nuclei -reset
    138 ```
    139 
    140 > **Warning — Template staleness:**
    141 > 1. Run `-ut` before every engagement — new CVEs land daily.
    142 > 2. `-nt` (new-templates) is great for re-scanning known targets for freshly-published CVEs only.
    143 > 3. There is **no `-tlds` flag** in nuclei — see Gotchas.
    144 
    145 ## Target Input
    146 
    147 ```bash
    148 # Single / multiple targets (comma-separated)
    149 nuclei -u https://example.com
    150 nuclei -u https://a.com,https://b.com
    151 
    152 # File of targets (one per line) — this is the "target file" flag
    153 nuclei -l urls.txt
    154 
    155 # Pipe from other ProjectDiscovery tools (the classic pipeline)
    156 subfinder -d example.com -silent | httpx -silent | nuclei -silent
    157 
    158 # Read a raw HTTP request (e.g. a Burp saved request) as input
    159 nuclei -l request.txt -im burp
    160 
    161 # Scan an entire subnet for network issues
    162 nuclei -u 192.168.110.0/24
    163 
    164 # Exclude hosts from the input list
    165 nuclei -l urls.txt -eh 10.10.10.5,10.10.10.6
    166 ```
    167 
    168 > **Input breakdown:**
    169 > 1. **-u / -target** — inline targets; accepts URLs, hosts, IPs, CIDRs.
    170 > 2. **-l / -list** — the file-based equivalent (this is what "target file" means — there is no `-target-file` flag).
    171 > 3. **stdin** — nuclei auto-reads piped input; disable with `-no-stdin`.
    172 > 4. **-im burp** — parse a saved Burp/HTTP request file instead of a plain URL list. (There is no standalone `-request` flag; use `-im burp` / `-im jsonl` / `-im openapi`.)
    173 
    174 ## Template Selection & Filtering
    175 
    176 ```bash
    177 # Run a specific template file, directory, or category
    178 nuclei -u https://target -t http/cves/
    179 nuclei -u https://target -t http/cves/ -t ssl/
    180 
    181 # Run a template straight from a URL
    182 nuclei -u https://target -turl https://example.com/my-template.yaml
    183 
    184 # Run a workflow (ordered, conditional template chain)
    185 nuclei -u https://target -w workflows/wordpress-workflow.yaml
    186 
    187 # Exclude a template file/dir
    188 nuclei -u https://target -et http/miscellaneous/
    189 
    190 # Tag-based include / exclude
    191 nuclei -u https://target -tags cve,rce
    192 nuclei -u https://target -etags dos,fuzz,intrusive
    193 
    194 # Force-run tags even if excluded by default config
    195 nuclei -u https://target -itags fuzz
    196 
    197 # Severity include / exclude
    198 nuclei -u https://target -s critical,high
    199 nuclei -u https://target -es info,low
    200 
    201 # Author filter
    202 nuclei -u https://target -a pdteam,geeknik
    203 
    204 # Template ID include / exclude (supports wildcards)
    205 nuclei -u https://target -id CVE-2021-44228
    206 nuclei -u https://target -id 'apache-*' -eid apache-detect
    207 
    208 # Expression-based template condition
    209 nuclei -u https://target -tc 'contains(tags,"cve") && severity=="critical"'
    210 
    211 # Only newly-added templates
    212 nuclei -u https://target -nt
    213 
    214 # Automatic scan: Wappalyzer tech detection → maps to matching template tags
    215 nuclei -u https://target -as
    216 ```
    217 
    218 > **Tip — Filtering strategy:**
    219 > 1. Start broad with `-as` to fingerprint tech, then re-run targeted `-tags`.
    220 > 2. Combine filters — `-tags cve -s critical,high` is the highest-signal quick pass.
    221 > 3. `-tc` (template-condition) is the power-user filter when tags/severity aren't precise enough.
    222 
    223 ## Output
    224 
    225 ```bash
    226 # Plain text file
    227 nuclei -u https://target -o findings.txt
    228 
    229 # JSONL to stdout (best for piping into jq / tooling)
    230 nuclei -u https://target -j
    231 
    232 # Export formats (write structured report files)
    233 nuclei -u https://target -je results.json      # JSON
    234 nuclei -u https://target -jle results.jsonl     # JSONL
    235 nuclei -u https://target -se results.sarif      # SARIF (for GitHub code scanning)
    236 nuclei -u https://target -me nuclei_report/     # Markdown dir
    237 
    238 # Clean, quiet output
    239 nuclei -u https://target -silent -nc
    240 
    241 # Verbose / debug
    242 nuclei -u https://target -v          # verbose
    243 nuclei -u https://target -vv         # show every template loaded
    244 nuclei -u https://target -debug      # dump all requests + responses
    245 
    246 # Save every request/response for later triage
    247 nuclei -u https://target -sresp -srd ./resp/
    248 ```
    249 
    250 > **Output breakdown:**
    251 > 1. **-silent + -nc** — the combo for clean logs you can paste into a report or feed to a script.
    252 > 2. **-je / -jle / -se / -me** — report *exports* (write a file); **-j** just changes stdout format.
    253 > 3. **-sresp / -srd** — stores raw req/resp — invaluable for confirming a finding isn't a false positive.
    254 > 4. **-debug** — use when a template *should* fire but doesn't; you'll see exactly what came back.
    255 
    256 ## Rate Limiting & Performance
    257 
    258 ```bash
    259 # Slow, polite scan for a fragile lab / CTF box
    260 nuclei -u https://target -rl 20 -c 10 -bs 10 -timeout 15 -retries 2
    261 
    262 # Requests-per-minute window (older -rlm is DEPRECATED; use -rld for duration)
    263 nuclei -u https://target -rl 300 -rld 1m
    264 
    265 # Aggressive scan for a robust target you own
    266 nuclei -l urls.txt -rl 500 -c 50 -bs 50
    267 
    268 # Tune host-error tolerance (skip dead hosts sooner)
    269 nuclei -l urls.txt -mhe 10
    270 nuclei -l urls.txt -no-mhe            # never skip a host on errors
    271 
    272 # Headless-browser scanning (DOM XSS, JS-heavy apps)
    273 nuclei -u https://target -headless -page-timeout 30
    274 nuclei -u https://target -headless -headc 5     # headless concurrency
    275 ```
    276 
    277 | Flag | Meaning | Default |
    278 |---|---|---|
    279 | `-rl` | Requests per second | 150 |
    280 | `-rld` | Rate-limit duration window | 1s |
    281 | `-bs` | Hosts in parallel per template | 25 |
    282 | `-c` | Templates in parallel | 25 |
    283 | `-timeout` | Per-request timeout (s) | 10 |
    284 | `-retries` | Retries per failed request | 1 |
    285 | `-mhe` | Max errors before skipping host | 30 |
    286 | `-headc` | Headless templates in parallel | 10 |
    287 | `-page-timeout` | Wait per page in headless (s) | 20 |
    288 
    289 > **Warning — Speed vs. stealth:**
    290 > 1. High `-rl`/`-c` will trip WAFs and can crash flaky HTB/CTF services.
    291 > 2. **`-headc` is headless concurrency** — do NOT confuse it with `-hc`, which is `-health-check`.
    292 > 3. On labs, prefer `-rl 20 -c 10` and raise it only if the target is stable.
    293 
    294 ## Network / Proxy
    295 
    296 ```bash
    297 # Route through Burp / a SOCKS5 pivot
    298 nuclei -u https://target -p http://127.0.0.1:8080
    299 nuclei -u https://target -p socks5://127.0.0.1:1080
    300 
    301 # Custom headers / cookies injected into EVERY http request
    302 nuclei -u https://target -H 'Authorization: Bearer eyJ...'
    303 nuclei -u https://target -H 'Cookie: session=abc123' -H 'X-Api-Key: secret'
    304 
    305 # TLS SNI override (virtual hosts / SNI-routed apps)
    306 nuclei -u https://10.10.10.10 -sni app.internal.htb
    307 
    308 # Custom resolvers + system fallback
    309 nuclei -l urls.txt -r resolvers.txt -sr
    310 
    311 # Network-scan interface / source IP (e.g. through a ligolo tun)
    312 nuclei -u 192.168.110.0/24 -i ligolo -sip 192.168.110.10
    313 ```
    314 
    315 > **Tip — Proxy + pivot:**
    316 > 1. Send nuclei through Burp with `-p` to record traffic and manually verify hits.
    317 > 2. On internal ranges reached via a Ligolo double tunnel, set `-i <tun>` so replies route back correctly.
    318 > 3. `-H` applies to every HTTP template — perfect for authenticated scans (see below).
    319 
    320 ## Interactsh / OOB
    321 
    322 Nuclei uses Interactsh for out-of-band (OAST) detection — blind SSRF, blind SQLi, RCE with no direct response, etc. By default it uses the public servers (`oast.pro`, `oast.live`, ...).
    323 
    324 ```bash
    325 # Point at your own self-hosted Interactsh server
    326 nuclei -u https://target -iserver https://oast.mydomain.com -itoken MYTOKEN
    327 
    328 # Disable OAST entirely (skips OAST-based templates) — offline / air-gapped labs
    329 nuclei -u https://target -ni
    330 ```
    331 
    332 > **Important — When to self-host or disable:**
    333 > 1. Self-host (`-iserver`/`-itoken`) when the target can't reach public OAST domains or you need to keep callbacks private.
    334 > 2. Use `-ni` on isolated lab networks with **no egress** — otherwise OAST templates just time out and slow the scan.
    335 
    336 ## Authentication
    337 
    338 Two ways to authenticate: quick header/cookie injection, or a structured **secret file** for multi-target auth.
    339 
    340 ```bash
    341 # Quick auth via headers/cookies
    342 nuclei -u https://app.target -H 'Authorization: Bearer <token>'
    343 nuclei -u https://app.target -H 'Cookie: PHPSESSID=<value>'
    344 
    345 # Structured secrets/auth file (per-domain creds, headers, cookies)
    346 nuclei -l urls.txt -sf secrets.yaml
    347 nuclei -l urls.txt -sf secrets.yaml -ps    # prefetch secrets before scanning
    348 ```
    349 
    350 ```yaml
    351 # secrets.yaml — example static auth strategy
    352 static:
    353   - type: header
    354     domains:
    355       - app.target.htb
    356     headers:
    357       - key: Authorization
    358         value: Bearer eyJ...
    359   - type: cookie
    360     domains:
    361       - app.target.htb
    362     cookies:
    363       - key: session
    364         value: abcdef123456
    365 ```
    366 
    367 > **Auth breakdown:**
    368 > 1. **-H** — simplest for a single authenticated target; header applies to all HTTP requests.
    369 > 2. **-sf** — scales auth across many domains and supports header/cookie/query/basic strategies.
    370 > 3. **-ps** — prefetch fires the auth flow up front so tokens are ready before templates run.
    371 > 4. Header casing is preserved from the secrets file — matters for case-sensitive APIs.
    372 
    373 ## Fuzzing / DAST Mode
    374 
    375 Nuclei's DAST mode runs **fuzzing templates** that inject payloads into parameters (query, body, headers, path) to find injection-class bugs. The old `-fuzz` flag is deprecated — use `-dast`.
    376 
    377 ```bash
    378 # Enable DAST / fuzzing templates
    379 nuclei -u 'https://target/search?q=test' -dast
    380 
    381 # Override the fuzzing behaviour set in the template
    382 nuclei -u 'https://target/?id=1' -dast -ft replace -fm single
    383 
    384 # Control fuzz aggression (payload volume) and scope
    385 nuclei -l urls.txt -dast -fa medium -cs '.*target\.htb.*'
    386 
    387 # Show which parameters are being fuzzed (debugging)
    388 nuclei -u 'https://target/?id=1' -dast -dfp
    389 ```
    390 
    391 | Flag | Meaning | Values |
    392 |---|---|---|
    393 | `-dast` | Enable DAST/fuzz templates | — |
    394 | `-ft` / `-fuzzing-type` | Override injection style | `replace,prefix,postfix,infix` |
    395 | `-fm` / `-fuzzing-mode` | Override combination mode | `multiple,single` |
    396 | `-fa` / `-fuzz-aggression` | Payload volume | `low,medium,high` (default `low`) |
    397 | `-cs` / `-fuzz-scope` | In-scope URL regex | regex |
    398 | `-cos` / `-fuzz-out-scope` | Out-of-scope URL regex | regex |
    399 | `-dfp` / `-display-fuzz-points` | Print fuzz points | — |
    400 
    401 > **Tip — DAST tips:**
    402 > 1. Feed DAST mode URLs **with parameters** — crawl first (e.g. with `katana`) so there's something to fuzz.
    403 > 2. Start at `-fa low`; raise only if you need deeper coverage — high aggression is loud.
    404 > 3. Combine with `-p` (Burp proxy) to inspect and replay interesting fuzz hits.
    405 
    406 ## Writing Custom Templates
    407 
    408 Every template needs three parts: **`id`**, an **`info`** block, and at least one **protocol block** (usually `http`).
    409 
    410 ```yaml
    411 id: example-panel-detect
    412 
    413 info:
    414   name: Example Admin Panel Detection
    415   author: netrunner
    416   severity: info
    417   description: Detects an exposed Example admin login panel.
    418   tags: panel,exposure,example
    419 
    420 http:
    421   - method: GET
    422     path:
    423       - "{{BaseURL}}/admin/login"
    424 
    425     matchers-condition: and
    426     matchers:
    427       - type: status
    428         status:
    429           - 200
    430       - type: word
    431         part: body
    432         words:
    433           - "Example Admin"
    434           - "Sign in"
    435         condition: or
    436 
    437     extractors:
    438       - type: regex
    439         part: body
    440         name: version
    441         group: 1
    442         regex:
    443           - 'v([0-9.]+)'
    444 ```
    445 
    446 > **Matcher types:**
    447 > 1. **word** — literal string(s) in a response part.
    448 > 2. **regex** — regular-expression match.
    449 > 3. **status** — HTTP status code.
    450 > 4. **size** — response length in bytes.
    451 > 5. **dsl** — expression logic, e.g. `duration >= 5`, `status_code==200 && len(body)>1000`.
    452 > 6. **binary** — hex pattern in binary responses.
    453 > 7. **xpath** — XPath query against XML/HTML.
    454 > 8. `matchers-condition: and|or` combines multiple matchers (default is `or`).
    455 
    456 > **Extractor types:**
    457 > 1. **regex** — pull data via regex (optional capture `group`).
    458 > 2. **kval** — grab a header/cookie by key.
    459 > 3. **json** — JQ-like extraction from JSON bodies.
    460 > 4. **xpath** — XML/HTML extraction (optional `attribute`).
    461 > 5. **dsl** — expression-based extraction, e.g. `len(body)`.
    462 > 6. Extractors capture dynamic values (CSRF tokens, session IDs) for reuse in later requests.
    463 
    464 ```yaml
    465 # Variables + payloads (fuzzing / brute) skeleton
    466 variables:
    467   useragent: "Mozilla/5.0"
    468 
    469 http:
    470   - method: GET
    471     path:
    472       - "{{BaseURL}}/search?q={{injection}}"
    473     headers:
    474       User-Agent: "{{useragent}}"
    475     attack: clusterbomb        # batteringram | pitchfork | clusterbomb
    476     payloads:
    477       injection:
    478         - "'"
    479         - "' OR '1'='1"
    480         - "' AND SLEEP(5)--"
    481     matchers:
    482       - type: dsl
    483         dsl:
    484           - "duration >= 5"
    485 ```
    486 
    487 ```bash
    488 # Validate a template before running it
    489 nuclei -validate -t my-template.yaml
    490 
    491 # Run your local template against a target
    492 nuclei -u https://target -t ./my-template.yaml
    493 
    494 # Run a template hosted at a URL
    495 nuclei -u https://target -turl https://raw.githubusercontent.com/.../my-template.yaml
    496 
    497 # Display a template's contents / list matches without scanning
    498 nuclei -t ./my-template.yaml -td
    499 nuclei -t ./my-template.yaml -tl
    500 ```
    501 
    502 > **Warning — Template gotchas:**
    503 > 1. Always `-validate` custom templates — a bad matcher silently produces no hits.
    504 > 2. `part:` matters (`body`, `header`, `all`, `response`) — matching the wrong part is the #1 "why won't it fire" bug.
    505 > 3. Signed/unsigned: `-dut` disables unsigned templates; your local custom ones are unsigned, so don't set `-dut` when testing them.
    506 
    507 ## Practical Recipes
    508 
    509 **Full recon pipeline: subfinder → httpx → nuclei** (the bread-and-butter external-recon chain):
    510 
    511 ```bash
    512 subfinder -d example.com -silent \
    513   | httpx -silent \
    514   | nuclei -silent -tags cve,exposure -s critical,high,medium -o findings.txt
    515 ```
    516 
    517 **Polite single-target scan (HTB / CTF box)** — slow rate, moderate concurrency, retries:
    518 
    519 ```bash
    520 nuclei -u http://10.10.10.10 -rl 20 -c 10 -bs 10 -timeout 15 -retries 2 -o box_scan.txt
    521 ```
    522 
    523 **CVE-only scan:**
    524 
    525 ```bash
    526 nuclei -u https://target -tags cve -s critical,high
    527 nuclei -u https://target -t http/cves/2024/
    528 ```
    529 
    530 **Tech-specific scan (fingerprint first, then target):**
    531 
    532 ```bash
    533 # Auto-detect tech and map to templates
    534 nuclei -u https://target -as
    535 
    536 # Or target a known stack by tag
    537 nuclei -u https://target -tags wordpress,wp-plugin
    538 nuclei -u https://target -tags apache,tomcat
    539 ```
    540 
    541 **Exposed panels & subdomain takeover:**
    542 
    543 ```bash
    544 # Login / admin panels
    545 nuclei -l urls.txt -tags panel,exposure
    546 
    547 # Subdomain takeover across a subdomain list
    548 subfinder -d example.com -silent | nuclei -tags takeover -silent
    549 ```
    550 
    551 **Scan against a saved Burp request:**
    552 
    553 ```bash
    554 # Export the request from Burp (Copy to file), then:
    555 nuclei -l burp_request.txt -im burp -tags cve,injection -dast
    556 ```
    557 
    558 ## Common One-Liners
    559 
    560 ```bash
    561 # Update engine + templates in one go
    562 nuclei -up && nuclei -ut
    563 
    564 # Quick high-signal pass on one target
    565 nuclei -u https://target -tags cve -s critical,high -silent -nc
    566 
    567 # Full pipeline, JSON export, quiet
    568 subfinder -d target.com -silent | httpx -silent | nuclei -j -je out.json -silent
    569 
    570 # Scan a list, exclude noisy/intrusive templates
    571 nuclei -l urls.txt -etags dos,fuzz,intrusive -es info -o clean.txt
    572 
    573 # Log4Shell / specific CVE across many hosts
    574 nuclei -l urls.txt -id CVE-2021-44228 -silent
    575 
    576 # Network subnet sweep through a ligolo tun
    577 nuclei -u 192.168.110.0/24 -i ligolo -tags network -o net.txt
    578 
    579 # DAST fuzz a parameterised URL through Burp
    580 nuclei -u 'https://target/?id=1' -dast -p http://127.0.0.1:8080 -dfp
    581 
    582 # Authenticated scan with a bearer token, save all responses
    583 nuclei -u https://app.target -H 'Authorization: Bearer TOKEN' -sresp -srd ./resp/
    584 
    585 # Dry-run: list which templates a filter would run
    586 nuclei -tl -tags cve -s critical
    587 
    588 # Re-scan known target for only newly-released templates
    589 nuclei -u https://target -nt -silent
    590 ```
    591 
    592 ## Troubleshooting & Gotchas
    593 
    594 > **Flags that don't exist / are easy to confuse:**
    595 > 1. **`-tlds`** — not a nuclei flag. Nuclei doesn't take a TLD list; scope is controlled by targets, `-eh`, and fuzz scope regex (`-cs`/`-cos`).
    596 > 2. **`-target-file`** — not a flag. The file-of-targets flag is **`-l` / `-list`**.
    597 > 3. **`-request`** — not a flag. Parse raw HTTP/Burp requests with **`-im burp`** (or `-im jsonl`/`-im openapi`).
    598 > 4. **`-hc`** — this is **`-health-check`**, *not* headless concurrency. Headless concurrency is **`-headc`**.
    599 > 5. **`-json`** — the JSON stdout flag is **`-j` / `-jsonl`**; file exports are **`-je`/`-jle`/`-se`/`-me`**.
    600 > 6. **`-template-url`** is **`-turl`** (not `-tu`).
    601 
    602 > **Common runtime issues:**
    603 > 1. **WAF trips / blocked mid-scan** → lower `-rl` and `-c`; add `-p` to watch the block in Burp.
    604 > 2. **False positives** → confirm with `-sresp`/`-debug`, then exclude with `-eid <id>`.
    605 > 3. **Stale results / missing new CVEs** → run `-ut`; use `-nt` to hit only fresh templates.
    606 > 4. **Noisy logs** → add `-silent -nc` for clean, scriptable output.
    607 > 5. **OAST templates hang on isolated labs** → add `-ni` to disable Interactsh.
    608 > 6. **JS/DOM-heavy app finds nothing** → try `-headless` (root on Linux disables the Chrome sandbox).
    609 > 7. **Host skipped early** → raise `-mhe` or use `-no-mhe` for flaky lab services.
    610 
    611 ## Lessons Learned
    612 
    613 1. **Confirm flags against `nuclei -h`, not memory** — several "obvious" flags (`-tlds`, `-target-file`, `-request`) don't exist, and short aliases collide (`-hc` ≠ headless).
    614 2. **Update templates before every scan** — nuclei's value is the community template feed; a stale feed misses this week's CVEs. Use `-nt` to re-check known targets cheaply.
    615 3. **Tune rate before scanning labs** — default `-rl 150` will hammer a fragile HTB/CTF box; `-rl 20 -c 10` is a safe starting point.
    616 4. **The `subfinder → httpx → nuclei` pipeline is the standard external-recon workflow** — pipe live hosts in via stdin and let nuclei do the detection.
    617 5. **Verify hits before reporting** — pair `-sresp`/`-debug` with a Burp proxy (`-p`) to rule out false positives, then `-eid` to suppress known noise.
    618 
    619 ## References
    620 
    621 - Nuclei Overview — https://docs.projectdiscovery.io/tools/nuclei/overview
    622 - Nuclei Installation — https://docs.projectdiscovery.io/tools/nuclei/install
    623 - Nuclei Command-Line Flags — https://docs.projectdiscovery.io/tools/nuclei/running
    624 - Nuclei GitHub — https://github.com/projectdiscovery/nuclei
    625 - Nuclei Templates — https://github.com/projectdiscovery/nuclei-templates
    626 - Matchers Reference — https://docs.projectdiscovery.io/templates/reference/matchers
    627 - Extractors Reference — https://docs.projectdiscovery.io/templates/reference/extractors
    628 - Interactsh (OAST) — https://github.com/projectdiscovery/interactsh
    629 - subfinder — https://github.com/projectdiscovery/subfinder
    630 - httpx — https://github.com/projectdiscovery/httpx