StackHawk alternative
A StackHawk alternative for MCP servers and Claude skills
StackHawk is one of the better dynamic application security testing (DAST) tools — its scanner stands up against your running API, crawls the routes, fires payloads at request parameters, and reports OWASP Top 10 findings against the live wire format. SkillAudit doesn't do any of that, because there's nothing for a DAST scanner to crawl on a Claude skill or an MCP server. The dangerous code is in the tool handlers, the attacker is the LLM's prompt context, and the install decision is pre-deploy. Different threat models, different scanners — and the one a team installing MCP servers actually needs is the second one.
TL;DR
StackHawk is a DAST scanner. It needs a running target with HTTP routes; it spiders, fuzzes parameters, and reports OWASP-shaped findings — XSS, SQL injection, broken auth, security headers, sensitive data in responses. That's the right model for a customer-facing REST or GraphQL API, and StackHawk is genuinely good at it. It's not the right model for a Claude skill or MCP server: most MCPs run over stdio (no HTTP surface to crawl), the threat is LLM-mediated content flowing into tool handlers (not a malformed query string), and the install decision happens before the server ever runs in your environment. SkillAudit reads the source — every server.tool(...) handler, every @app.tool function, every fetch(args.url) SSRF site — and grades the repo on the same six axes (security, permissions, credentials, maintenance, client compatibility, docs) before you claude plugin install. We've graded 101 of the most-installed MCP servers this way. 50% shipped SSRF, 38% had credential-handling findings, 19% earned an A. StackHawk in CD against your customer-facing API; SkillAudit in CI against the agent code that runs inside your trust boundary.
Why teams look for a StackHawk alternative for Claude skills and MCP servers
StackHawk is well-positioned for what it does — DAST in CD pipelines, scanning the running API after deploy to a staging environment, catching the regression where a refactor reintroduced an injection sink that static analysis missed. Teams that build customer-facing APIs and need a black-box runtime scanner alongside their SAST tools have good reasons to keep using it.
But ICP buyers and authors keep landing on three structural reasons DAST as a category — StackHawk included — doesn't fit the install decision for Claude skills and MCP servers:
- There's nothing for a DAST scanner to crawl. The most common MCP transport is stdio: the LLM client (Claude Code, Cursor, Windsurf) launches the server as a child process and exchanges JSON-RPC frames over stdin and stdout. There is no HTTP listener. There are no routes. There is no spider target. StackHawk is built around HTTP / GraphQL / gRPC / SOAP introspection — every one of those assumes a wire surface that an MCP server simply doesn't expose. Even when an MCP server does serve over HTTP / SSE, it presents a single JSON-RPC endpoint that doesn't enumerate; the "API surface" — the tools — is described inside the protocol's
tools/listresponse, not in a routing table the spider can read. - The attacker model is wrong. A DAST scanner simulates an external, untrusted web client sending malformed inputs. The relevant attacker on an MCP install is different: an attacker plants malicious content in a place an LLM will read it as data — a webpage the agent fetches, a Slack message it summarises, a GitHub issue it triages. The content carries an instruction. The LLM, with that instruction now in its working context, calls a tool that the MCP server exposes. The vulnerability is "the tool happily exfiltrates the secret in the environment, or rewrites a config, or fetches an internal URL, because the LLM was tricked." DAST has no model of this. The malicious payload isn't on the wire; it's in the prompt, three turns back.
- The decision happens before the server runs. A team adopting an MCP server is making an install-time decision. They want a signal that says "is this safe to install" before
claude plugin installdrops the code into the agent's trust boundary. DAST is post-deploy by construction — you need the server running, often with credentials wired up, to scan it. By the time DAST could fire, the secrets are already in the environment and the install decision is already made.
Three buyer-side reasons we hear:
- You install MCP servers before you'd know to set up DAST. The buying motion for a Claude skill is "paste the GitHub URL into Claude Code's plugin manager." That decision needs a pre-install signal, not a post-deploy crawl.
- Your DAST tool flags zero issues on a stdio MCP. It can't help — there's no surface to scan. You need a static scanner for the source, and a prompt-injection probe that simulates the LLM-mediated attacker.
- You want a public per-repo grade buyers can read on the README. DAST findings are private and tied to your environment. SkillAudit's report card is a public, stable URL.
How SkillAudit is different
SkillAudit is a static + LLM-assisted scanner built specifically for the install-time decision on Claude skills and MCP servers. It reads the source — TypeScript, Python, Go, Rust, the nine languages that ship official MCP SDKs — and locates every server.tool(...) registration, every @app.tool decorator, every handler body, every fetch() call inside a handler. Then it runs the seven checks that compose into a single A–F grade:
- SSRF — does any tool handler call
fetch()/http.request()/urllib.urlopen()with a URL the LLM can control? - Command-exec —
shell=True,execSync,os.system,subprocess.Popenwith shell-interpreted strings? - Prompt injection — an LLM-assisted probe (Claude Haiku 4.5) red-teams each handler, looking for paths where untrusted content can flow into a tool response that the agent will treat as more instructions.
- Credential echo — does
process.env.Xoros.environ['X']appear on any return path of a tool handler? - Permission scope — does the server ask for org-wide OAuth scopes when single-repo would do?
- Maintenance — last commit, open issues, advisory feed.
- Client compatibility — non-standard transports, protocol-version mismatches across Claude Code / Cursor / Windsurf / Codex.
Output is a single A–F grade plus a public report card at a stable URL with file paths and finding counts. Run time: roughly 60 seconds. It runs without standing up a target environment, without provisioning credentials, without a CD pipeline — paste a URL, get a graded report, decide whether to install.
Side by side
| StackHawk | SkillAudit | |
|---|---|---|
| Scanner type | DAST — runtime, black-box, requires a running target | Static + LLM-assisted — reads source, no running server |
| Threat model | External web client probing HTTP / GraphQL / gRPC / SOAP | LLM-mediated attacker via untrusted content flowing into tool handlers |
| Primary axis | OWASP Top 10 against a deployed API | Six-axis MCP rubric: security, permissions, credentials, maintenance, client compat, docs |
| What it reads | Live HTTP responses from a running app | Source files — every server.tool / @app.tool handler |
| stdio MCP servers | Cannot scan — no HTTP surface to crawl | Yes — reads source regardless of transport |
| HTTP / SSE MCP servers | Could spider the JSON-RPC endpoint, but tools aren't enumerable as routes | Yes — reads tool registrations directly from source |
SSRF in fetch(args.url) tool handlers | Catchable only if you trick the LLM into calling the tool with a probe payload — post-install | Yes — pattern check fires statically; first-class axis |
| Command-exec in tool handlers | Same — needs LLM-mediated invocation against a running server | Yes — flags shell=True, execSync, os.system in handler bodies |
| Prompt-injection susceptibility | Not in scope — no model of the LLM-as-instruction-channel attack | Yes — Claude Haiku 4.5 red-teams every extracted handler |
Credential echo from process.env | Catchable only by the live response, if probed correctly | First-class axis; flags env vars on handler return paths |
| Maintenance / repo signals | Not in scope | Last commit, open issues, advisory feed; per-axis |
| Client compatibility | Not in scope | Yes — non-standard transports + protocol-version mismatches |
| Setup before scan | Stand up target env, configure auth, define routes, manage secrets | Paste a public GitHub URL — runs in 60s, no target needed |
| Public per-repo report card | No — findings live in the StackHawk app, tied to your env | Yes — stable URL with file paths and finding counts |
| Embeddable badge for authors | No public-facing badge model | Yes — A–F badge updates per scan |
| Pricing | Free tier; paid plans by app/scan/seat | Free: 3 audits/mo public · Pro $19/mo · Team $99/mo |
The shape of the gap, in 30 seconds
The simplest way to see why DAST and MCP scanning aren't substitutes is to look at the canonical SSRF in an MCP tool handler:
// Common SSRF idiom in a Claude skill / MCP server.
// Clean under DAST (no HTTP surface to crawl on stdio).
// F-grade SSRF under SkillAudit (handler reads source).
import { McpServer } from "@modelcontextprotocol/sdk/server/mcp.js";
const server = new McpServer({ name: "fetch-helper", version: "1.0" });
server.tool(
"fetch_url",
"Fetch the contents of any URL",
{ url: z.string() },
async ({ url }) => {
const res = await fetch(url); // SSRF
const body = await res.text();
return { content: [{ type: "text", text: body }] };
}
);
server.connect(new StdioServerTransport());
For a DAST tool to fire on this, three things have to be true: the server has to expose an HTTP listener (it doesn't — stdio), the scanner has to know which tool to call (it doesn't — tools aren't routes the spider can enumerate), and the scanner has to coax the LLM into invoking the tool with the probe URL (StackHawk doesn't model the agent loop). The same handler is a one-line static catch — a fetch() with an LLM-controlled argument inside a tool registration. SkillAudit reads it directly from source, files a finding, and the repo lands on the public board with the file path and a grade.
It's not that DAST is bad — it's that the gap between "running web app probed from outside" and "Claude skill installed into an agent's trust boundary" is wide enough that an entirely different class of scanner is needed. SkillAudit was built to fill that gap.
What the data says
We ran SkillAudit against 101 of the most-installed Claude skills and MCP servers — the full live board is public and growing. The corpus includes vendor-official releases (Stripe, PayPal, MongoDB, Redis, Cloudflare, AWS, Azure, GCP, Heroku, Notion, Snowflake, Pinecone, Couchbase, Auth0, Resend, Brave, Vectara, Meilisearch, plus Anthropic's nine official MCP language SDKs), popular indie frameworks (FastMCP, mcp-use, mcp-agent), and community releases.
Results: 50% (50/101) shipped SSRF findings, 38% (38/101) had credential-handling findings, 10% (10/101) had command-exec findings, only 19% (19/101) earned an A. Full grade distribution: 19 A · 30 C · 10 D · 42 F. Methodology and per-repo grades are in our research post: The state of MCP server security, 2026.
The relevant point for the StackHawk comparison: every one of those findings is in source code, in a tool handler, that DAST has no surface to reach. Most of the F-grade repos in the corpus run over stdio — there's literally nothing for a runtime scanner to crawl. A few serve over HTTP / SSE, but the JSON-RPC endpoint hides the tools behind tools/call arguments that DAST spiders can't enumerate. The threat surface MCP introduced is, by construction, a static-analysis problem.
When StackHawk is still right
StackHawk earns its keep on a different problem. Specifically:
- You're protecting a customer-facing REST / GraphQL / gRPC / SOAP API. DAST is the right scanner — runtime probing against the deployed app catches the OWASP Top 10 issues your SAST tool may have missed. StackHawk is a credible choice in that category.
- You need post-deploy regression scanning. SAST alone misses bugs introduced by deployment configuration, infrastructure changes, or environment-specific quirks. DAST in CD against staging closes that gap. SkillAudit can't substitute for a runtime scan of your production API.
- You want auth-flow and session-management testing. Things like CSRF, broken authentication, session fixation, missing security headers — these are wire-format questions that need a live target. Static analysis can hint at them; DAST validates them.
- You're testing an HTTP-shaped service that happens to have an MCP wrapper. If the MCP server is a thin facade over a customer-facing API and you're worried about that API's HTTP surface — that's the API's job to scan, and StackHawk fits. SkillAudit will still fire on the MCP wrapper itself, but the underlying API needs DAST.
- You're already shipping mature SAST + DAST in CI/CD. Don't rip that out — it's covering different ground. Add SkillAudit alongside, the same way you added Snyk alongside your DAST a few years ago when supply-chain risk became its own category.
The most useful framing: StackHawk runs against the public-facing app you ship; SkillAudit runs against the MCP servers and Claude skills you install. Different code, different threat models, different points in the SDLC. Run both, in different jobs, in different pipelines.
Workflow
Three steps to add SkillAudit on top of your existing DAST setup:
- Keep StackHawk in CD. If it's already gating your customer-facing API in staging, leave it alone. SkillAudit doesn't replace it; the threat surface is different.
- Add SkillAudit as a pre-install gate. Before
claude plugin install, paste the URL into SkillAudit (or wire the GitHub Action — Pro plan) to gate adoption on a minimum grade. The first time most teams run this, they reject 30-50% of the MCPs they were planning to install. The grade tells you which. - Treat SkillAudit and DAST as different jobs. StackHawk in your
deploystage against the running staging API; SkillAudit in a separateplugin-auditstage that runs whenever.claude/plugins.lockchanges. The two never collide; they cover different code paths and different threat models.
Indie developers shipping MCP servers can run SkillAudit at zero cost — the free tier covers three audits a month on public repos, and the public report card is shareable on your README the same day you publish. Buyers gate adoption with the public grade; authors embed the badge to win listings.
Try SkillAudit on your repo — free
Paste any GitHub URL on the home page, get a graded report card in 60 seconds. Your repo joins the public board only if you opt in; private repos audit through a single-repo OAuth scope, never org-wide.