The finding that started it

During a scan of a live target, ReconX reported a critical finding: Spring4Shell remote code execution on an internal API host. Critical severity. High confidence in the raw output. The kind of line that pages an on-call engineer at 2am.

It was completely wrong.

The template behind it probed a class-loader URL and matched on a single rule: HTTP 200, and the response body does not contain the word “error”. The host in question was a JSON API that answers {} to almost any GET. Empty object, status 200, no “error” string. The signature fired. A brochure of a finding, dressed as a breach.

This is the failure mode that makes people distrust automated scanners. Not missing a real bug. Reporting a fake one as if it were proven.

Two layers, because one is not enough

We already had AI-based false-positive validation. It works well, but it only runs when you configure an API key. Plenty of scans run without one, and those scans were shipping raw scanner output with zero filtering. That is exactly when a fake critical does the most damage.

So we added a second layer that always runs: a deterministic verification pass. No API key. No extra requests to the target. It re-reads each finding against the evidence already captured during the scan and asks a simple question: does the proof actually support the claim?

Three checks cover the most common ways a signature lies:

  1. Empty-body exposures. A finding that claims a sensitive resource is “accessible” but whose response body is empty is not evidence of anything. An ACME challenge directory, a single-page-app catch-all, and a locked-down endpoint all return 200 with nothing useful. That is not a leak.

  2. Content-type contradictions. A finding that claims an exposed Swagger or OpenAPI document, served as text/html with none of the actual API-spec markers, is almost always a single-page-app shell answering 200 for every path. Grafana does this. GitLab does this. The word “swagger” appearing somewhere in a JavaScript bundle is not an exposed API spec.

  3. Unproven exploit claims. A high-severity remote-code-execution or CVE finding whose only proof is a trivial or empty body did not demonstrate exploitation. It demonstrated the absence of an error message. Real code execution leaves evidence: reflected command output, an out-of-band callback, a specific stack trace.

Downgrade, never delete

The important design choice: a flagged finding is never dropped. It stays in the report, downgraded to tentative and tagged as unverified and likely false positive, with a one-line reason attached.

A verifier that silently deletes findings is its own kind of danger. If the heuristic is wrong, a deleted finding is a hidden real vulnerability. A downgraded and labelled finding is still on the page for a human to overrule. The reader loses nothing and gains a triage lane.

On that Spring4Shell finding, both layers now catch it. The template was rewritten to require the genuine Spring data-binding side effect (an HTTP 500 with a Spring stack-trace marker), so it no longer fires on an empty {}. And even if a future template misbehaves the same way, the deterministic pass downgrades any unproven critical to a clearly labelled maybe.

Honest coverage, too

The same principle drove two smaller changes in this release.

Reports now disclose scan coverage directly: how many discovered hosts returned testable surface versus how many were WAF-gated or blank. A report that says “15 findings across 23 subdomains” implies all 23 were assessed. If 21 of them are walls that return nothing, the reader deserves to know that, not to infer a clean bill of health that was never earned.

And the executive summary no longer leans on an AI key to be useful. Without one, ReconX now writes a real deterministic summary: the actual top findings by name, the coverage caveat, and a severity-ordered remediation roadmap, in place of the generic boilerplate that used to fill the gap.

The lesson

Good security tooling is not measured only by what it catches. It is measured by whether you can trust what it tells you. A single fake critical erodes that trust faster than ten real findings build it.

The full release also ships deep reconnaissance mode, which enumerates an entire subdomain estate and scans every live host rather than a handful. See the changelog for everything in this version.