From a164d5b50076d35af7036bc5be2b6c2507fc82ae Mon Sep 17 00:00:00 2001 From: Naboot42 Date: Fri, 3 Jul 2026 17:11:22 +0200 Subject: [PATCH] feat(api_discover): hand off discovered OpenAPI specs to nuclei When api_discover finds an exposed OpenAPI/Swagger spec, the new --spec option routes it to nuclei with input-mode=openapi + DAST fuzzing, which parses the spec and fuzzes every documented endpoint with the correct method/parameters. This recovers the contextual API testing kiterunner used to provide, using a maintained tool already integrated in secator (no new dependency). - nuclei task: add a `dast` flag (-dast) to enable fuzzing templates. - api_discover.yaml: add --spec option and a nuclei step targeting discovered spec URLs (openapi/swagger/api-docs), gated behind --spec. Co-Authored-By: Claude Opus 4.8 (1M context) --- secator/configs/workflows/api_discover.yaml | 22 ++++++++++++++++++--- secator/tasks/nuclei.py | 1 + 2 files changed, 20 insertions(+), 3 deletions(-) diff --git a/secator/configs/workflows/api_discover.yaml b/secator/configs/workflows/api_discover.yaml index 7a43d9783..17629f78f 100644 --- a/secator/configs/workflows/api_discover.yaml +++ b/secator/configs/workflows/api_discover.yaml @@ -8,9 +8,9 @@ long_description: | brute-forcing of API routes (ffuf, using Assetnote's HTTP Archive apiroutes wordlist — the same real-world route dataset kiterunner relied on). Discovered endpoints are probed with httpx to verify they are live and fingerprint their technologies. The apiroutes wordlist also covers exposed API specification paths - (openapi/swagger), so they surface when fuzzing is enabled. Endpoint discovery only — parameter fuzzing, - vulnerability scanning and secrets hunting are handled by the url_params_fuzz and url_vuln workflows (see - the `api` scan). + (openapi/swagger); when one is found, the --spec option hands it off to nuclei, which parses the spec + (input-mode openapi) and DAST-fuzzes every documented endpoint with the correct method and parameters — + recovering the contextual testing kiterunner used to provide, using a maintained tool already in secator. tags: [http, api, crawl, fuzz] input_types: - url @@ -30,6 +30,12 @@ options: default: False short: fuzz + spec: + is_flag: True + help: Hand off discovered OpenAPI/Swagger specs to nuclei for endpoint fuzzing (combine with --fuzz to find them) + default: False + short: spec + tasks: katana: description: Crawl for API endpoints @@ -56,3 +62,13 @@ tasks: - type: url field: url condition: not url.verified + + nuclei: + description: Fuzz endpoints from discovered API specs + input_mode: openapi + dast: True + targets_: + - type: url + field: url + condition: "'openapi' in url.url or 'swagger' in url.url or 'api-docs' in url.url" + if: opts.spec diff --git a/secator/tasks/nuclei.py b/secator/tasks/nuclei.py index bff3ed4d2..2d9773096 100644 --- a/secator/tasks/nuclei.py +++ b/secator/tasks/nuclei.py @@ -41,6 +41,7 @@ class nuclei(VulnMulti): opts = { 'automatic_scan': {'is_flag': True, 'short': 'as', 'help': 'Automatic web scan using wappalyzer technology detection to tags mapping'}, # noqa: E501 'bulk_size': {'type': int, 'short': 'bs', 'help': 'Maximum number of hosts to be analyzed in parallel per template'}, # noqa: E501 + 'dast': {'is_flag': True, 'default': False, 'help': 'Enable DAST fuzzing templates (required to fuzz OpenAPI/Swagger endpoints)'}, # noqa: E501 'debug': {'type': str, 'help': 'Debug mode'}, 'display_templates': {'is_flag': True, 'default': False, 'short': 'dt', 'help': 'Display loaded template names.'}, 'exclude_severity': {'type': str, 'short': 'es', 'help': 'Exclude severity'},