npx afterpack@latest audit <url> fetches the JavaScript a site ships and reports what a reader can pull out of it. It is the same scanner that powers the public security scanner: exposed secrets, leaked source maps, protection level, dangerous patterns, detected stack, and known CVEs.
Audit is read-only. It modifies nothing, needs no account, and touches only what the URL serves publicly.
audit does not run the obfuscation engine. It fetches a site's shipped assets and analyzes what is already exposed. None of the build flags apply to it.
Run it
$ npx afterpack@latest audit https://yoursite.comThe scheme is optional: a bare hostname is normalized to https://. The scanner fetches the page, renders it so client-side-loaded bundles are included, then analyzes every JavaScript resource it found.
There is no local-directory mode. npx afterpack@latest audit ./dist is not supported. The argument must be a URL. Audit a preview deployment instead.
What it checks
| Check | What it finds |
|---|---|
| Exposed secrets | AWS keys, private keys, JWTs, Stripe / OpenAI / GitHub / GitLab / Slack / Google / SendGrid / Twilio / Mailgun / LaunchDarkly credentials, database URLs, bearer tokens, internal URLs, Firebase config, and high-entropy strings, around two dozen patterns. |
| Exposed source maps | Shipped .map files reachable from the bundle. |
| Protection level | How protected the shipped JavaScript is: plain, minified only, or actually obfuscated. The per-token version of this question is the Protection Map. |
| Dangerous patterns | eval(), the Function constructor, document.write, innerHTML assignment and similar high-risk JavaScript APIs found in the shipped bundles. |
| Detected tech stack | Frameworks and libraries fingerprinted from the bundle. |
| Known CVEs | Published vulnerabilities in the dependency versions it detects. |
Exposed source maps
A source map chains your shipped bundle back to your original, readable source. Never ship one to production: an attacker downloads it and reads your code as you wrote it.
Audit catches it. AfterPack itself writes no .map sibling in a production build by default (see sourceMap.enabled and sourceMap.emitUrl), but it cannot stop your bundler from having already emitted one.
Reading the results
The CLI prints each phase as it completes, surfaces critical and high findings inline as they arrive, then closes with a summary box: score out of 100, resource counts, findings by severity, detected stack, and readability. It ends with a list of every critical finding and a link to the full report on the web.
Read it top-down:
- Secrets and source maps first. These are the findings that make obfuscation pointless. Rotate any leaked secret, then stop shipping it; remove any
.mapfrom production. - Protection level next. If the bundle reads as plain or merely minified, it has no meaningful protection. Run a build through AfterPack (Quickstart takes about five minutes).
- CVEs and dangerous patterns last. Triage by severity; not every match is exploitable, but each is something a reader can see.
Output is human-readable text by default. --diagnostics.format=json puts one JSON document on stdout instead — the findings, the score and the report link — with every human-readable line moved to stderr; --diagnostics.level=none silences the progress phases on top of that. The shareable report is always the web link the run ends with.
Exit codes
| Code | When |
|---|---|
0 | The scan completed. Including when it found critical issues. |
1 | The scan failed: an unreachable URL, a server-side error, the daily rate limit, or a stream that ended without completing. |
64 | Misuse: no URL given, more than one URL, or the URL is malformed. |
These are audit's own codes. The build exit codes an obfuscation run uses are separate.
Because a completed scan exits 0 regardless of what it found, npx afterpack@latest audit … && deploy does not fail on findings. There is no severity threshold flag: read the findings from --diagnostics.format=json yourself if you want to gate on them. Use audit as a pre-release review step you read manually. The obfuscation run is the part that fails a build.
Unauthenticated scans are limited to 3 per IP per 24 hours. Hitting the limit prints how long to wait and exits 1.
Next
- Builds & CI: baking obfuscation into your release pipeline, and pinning a seed for reproducible output.
- Best practices: what to mark, what to leave alone, and the source-map rule.
- Security scanner: the same checks in your browser, no install, with the full shareable report.
- Protection Map: the per-token view of your own build, once you're obfuscating.
- What AfterPack does not replace: a leaked secret needs rotation; obfuscating it after the fact does not help.