惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

T
Tenable Blog
K
Kaspersky official blog
cs.AI updates on arXiv.org
cs.AI updates on arXiv.org
T
The Exploit Database - CXSecurity.com
Cisco Talos Blog
Cisco Talos Blog
P
Palo Alto Networks Blog
Latest news
Latest news
cs.CL updates on arXiv.org
cs.CL updates on arXiv.org
C
CXSECURITY Database RSS Feed - CXSecurity.com
P
Privacy International News Feed
The Hacker News
The Hacker News
T
Tor Project blog
www.infosecurity-magazine.com
www.infosecurity-magazine.com
C
Cisco Blogs
阮一峰的网络日志
阮一峰的网络日志
Recent Commits to openclaw:main
Recent Commits to openclaw:main
博客园_首页
N
News and Events Feed by Topic
W
WeLiveSecurity
罗磊的独立博客
GbyAI
GbyAI
T
Troy Hunt's Blog
Y
Y Combinator Blog
Recorded Future
Recorded Future
The Cloudflare Blog
TaoSecurity Blog
TaoSecurity Blog
爱范儿
爱范儿
美团技术团队
Attack and Defense Labs
Attack and Defense Labs
C
Check Point Blog
Engineering at Meta
Engineering at Meta
Cyberwarzone
Cyberwarzone
Cyber Security Advisories - MS-ISAC
Cyber Security Advisories - MS-ISAC
F
Fortinet All Blogs
The GitHub Blog
The GitHub Blog
奇客Solidot–传递最新科技情报
奇客Solidot–传递最新科技情报
Apple Machine Learning Research
Apple Machine Learning Research
Know Your Adversary
Know Your Adversary
AWS News Blog
AWS News Blog
D
DataBreaches.Net
Recent Announcements
Recent Announcements
K
KPMG report finds enterprise disconnect between AI and its ROI | CIO
M
MIT News - Artificial intelligence
Webroot Blog
Webroot Blog
Security Latest
Security Latest
T
Tailwind CSS Blog
V2EX - 技术
V2EX - 技术
aimingoo的专栏
aimingoo的专栏
S
Security @ Cisco Blogs
Exploit-DB.com RSS Feed
Exploit-DB.com RSS Feed

DEV Community

Authentication Security Deep Dive: From Brute Force to Salted Hashing (With Java Examples) Why AI Systems Don’t Fail — They Drift Spilling beans for how i learn for exam😁"Reinforcement Learning Cheat Sheet" I Replaced Chrome with Safari for AI Browser Automation. Here's What Broke (and What Finally Worked) How Python Borrows Other People's Work The $40 Architecture: Processing 1 Billion API Requests with 99.99% Uptime Vibe Coding: A Workflow Guide (From Zero to SaaS) Most webhook security guides protect the wrong side. The scary part is delivery. Headless CMS for TanStack Start: Build a Blog with Cosmic EU Age Verification App "Hacked in 2 Minutes" — What Actually Happened Comfy Cloud’s delete function does not actually remove files Running AI Models on GPU Cloud Servers: A Beginner Guide Event-driven media intelligence with AWS Step Functions and Bedrock I scored 500 AI prompts across 8 quality dimensions — here's what broke How to Call Google Gemini API from Next.js (Free Tier, No Backend Needed) The Portal Protocol: Reclaiming Human Connection in the Age of AI How to Fix Your Team's Scattered Knowledge Problem With a Self-Hosted Forum Intro to tc Cloud Functors: A Graph-First Mental Model for the Modern Cloud Designing Multi-Tenant Backends With Both Ownership and Team Access I Built a Neumorphic CSS Library with 77+ Components — Here's What I Learned PostgreSQL Performance Optimization: Why Connection Pooling Is Critical at Scale Cómo construí un SaaS multi-rubro para gestionar expensas en Argentina con FastAPI + Vue 3 🚀 I Built an Ethical Hacking Scanner Tool – Open Source Project I Replaced /usage and /context in Claude Code With a Single Statusline A Pythonic Way to Handle Emails (IMAP/SMTP) with Auto-Discovery and AI-Ready Design I Collected 8.9 Million Polymarket Price Points — Here's What I Found About How Markets Really Move EcoTrack AI — Carbon Footprint Tracker & Dashboard Everyone's Using AI. No One Agrees How. 5 self-hosted ebook managers worth trying in 2026 Building Your First AI Agent with LangChain: From Chatbot to Autonomous Assistant Common SOC 2 Failures (Real World) Stop Vibe-Checking Your AI App: A Practical Guide to Evals How to Use SonarQube and SonarScanner Locally to Level Up Your Code Quality Your Next To-Do App Is Dead — I Replaced Mine with an OpenClaw AI Sign a Nostr event in 60 lines of Python using coincurve — no nostr-sdk, no nbxplorer, no rust toolchain ITGC Audit Explained Like You’re in Big 4 Patch Tuesday abril 2026: Microsoft parcha 163 vulnerabilidades y un zero-day en SharePoint Stop scraping everything: a better way to track competitor price changes Listing on MCPize + the Official MCP Registry while routing payments OUTSIDE the marketplace — how I kept 100% of my x402 revenue Building an AI-Powered Risk Intelligence System Using Serverless Architecture Why We Ripped Function Overloading Out of Our AI Toolchain Testing AI-Generated Code: How to Actually Know If It Works SaaS Churn Is Killing Your Business. Here Is What to Do About It (Without a Support Team) The Speed of AI Is No Longer Linear - And Self-Improving Models Are Why How to Implement RBAC for MCP Tools: A Practical Guide for Engineering Teams From Standard Quote to Persuasive Proposal: AI Automation for Arborists I built a CLI that scaffolds complete multi-tenant SaaS apps Axios CVE-2025–62718: The Silent SSRF Bug That Could Be Hiding in Your Node.js App Right Now The dashboard that ended our friendship Data Pipelines Explained Simply (and How to Build Them with Python) The Hidden Cost of AI Systems Nobody Talks About. undefined vs undeclared, and how typeof behaves Switching from file-based jobs to NATS/Kafka in Rust without changing code io_uring Adventures: Rust Servers That Love Syscalls Why Agentic AI is Killing the Traditional Database The POUR principles of web accessibility for developers and designers Quantum Neural Network 3D — A Deep Dive into Interactive WebGL Visualization How To Install Caveman In Codex On macOS And Windows Automation Pipeline Reliability: Why Your Workflow Breaks When Nobody Is Watching I Built an 'Open World' AI Coding Agent — It Works From ANY Folder From Freelancing to Product: A Tech Service Company's SaaS Transformation China's AI Giants: Adding Tencent Hunyuan & ByteDance Doubao to AI University (74 Providers) On the Vibe Coders and Their Lies clerk: Auto-Summarize Your Claude Code Sessions AI Weekly — 2026/04/10–04/17 | The Model Lockdown Is Here, but the Toolchain Is the Real Battleground AI 週報 — 2026/04/10–2026/04/17 模型封鎖潮來了,但工具鏈才是真戰場 Maybe this is how Open-Source apps are born... 🚀 Fine-Tune LLMs with LoRA and QLoRA: 2026 Guide tRPC v11 + Next.js App Router: End-to-End Type Safety Without the Boilerplate ShadCN UI in 2026: Why I Stopped Installing Component Libraries and Started Owning My Components SaaS Billing in React Server Components: Stripe + Supabase Without a Single `useEffect` Join our DEV Weekend Challenge — $1,000 in Prizes Across TEN winners! Submissions Due April 20 at 6:59 AM UTC. Implementing FSRS Spaced Repetition in Flutter + Supabase — Adding Memory Science to an AI Learning App "I Texted My Localhost From the Train — Claude Code Fixed the Bug Before I Got Home" I Built a Sales Prep AI and It Went Deeper Than Expected Design to Code #2: One JSON, Eleven Outputs Solving the 100M-Row Problem: A Summary Table Pattern for High-Volume Push Notification Logs Flutter Web With Wasm: What Actually Changes For Developers I Built 50 Royalty-Free Soundtracks for My Side Project in a Weekend Using AI Music Generation The Vibe Coding Security Checklist: 7 Things to Check Before You Ship Stop Letting Googlebot Guess Fix Your React App's SEO Right Desconstruindo o Streaming do LinkedIn: Como Criar um Engine de Extração de Vídeo de Alta Performance com HLS e FFmpeg (EDA Part-1) EDA (Exploratory Data Analysis) Explained With Real Life — Why Looking at Your Data Is the Most Important Step in Machine Learning Brand Relationship Management at Scale: Our 4-Touch Outreach System for 200+ Brands Why String.fromEnvironment() Might Return an Empty String in Dart JGuardrails 1.0.0 — Hardening Java LLM Apps Against Jailbreaks, Toxicity, and Prompt Injection Plan and Schedule a Full Week of Threads Content From One Claude Conversation Coding Cat Oran Ep3, Five Tables Changed Everything Updated: BFF Pattern I'm done watching freelancers get buried by 200 proposals. So I'm building the alternative. This is my first post BFS Algorithm in Java Step by Step Tutorial with Examples Tracking LLM Pricing Monthly: An Open Dataset for 22 AI Models How We Measure Content ROI on a Comparison Site: Revenue Attribution Without Perfect Data Introducing Nova AI Ops: The AI-Native Operating System for SRE Teams I built a free desktop video downloader for Windows — Grabbit How Talkie OCR Helps Vision-Impaired & Dyslexic Users Read the World Around Them VRCFaceTracking安装和iPhone面捕配置教程,有bug Even CrowdStrike Can't See Your Agents The Automation Gold Rush: What n8n Workflows and Claude Are Opening Up for Developers Right Now
The MCP Security Crisis: What We Found Hunting Vulnerabilities Across the Ecosystem
AKAVLABS · 2026-04-28 · via DEV Community

The MCP Security Crisis: What We Found Hunting Vulnerabilities Across the Ecosystem

By Akav Labs | AgentSentry Research


The Model Context Protocol is quietly becoming the nervous system of enterprise AI. In the span of a few months, every major infrastructure company shipped an MCP server — Microsoft, MongoDB, Auth0, Cloudflare, ClickHouse, Upstash. Enterprises are connecting these servers to their LLM agents and pointing them at production databases, CI/CD pipelines, and authentication systems.

Nobody audited them first.

We spent several days doing systematic security research across the MCP ecosystem. What we found was not a collection of isolated bugs. It was the same classes of vulnerability, reproduced across vendor after vendor, suggesting that the ecosystem shipped fast and security thinking came later. This post documents the attack patterns we identified, the methodology we used, and what we believe needs to change.

We are not naming specific vendors or CVE numbers in this post. Coordinated disclosure windows are active. When those windows close, the full technical advisories will be published. What we can share now is the methodology and the vulnerability classes — which we believe are present across far more MCP servers than the ones we examined.


Background: What MCP Actually Is

For readers who haven't worked with it directly: the Model Context Protocol is a specification from Anthropic that standardizes how LLM agents communicate with external tools and data sources. An MCP server exposes a set of "tools" — functions the agent can call to read data, write data, or trigger actions. The agent decides which tools to call based on what it's trying to accomplish.

The security model is implicit. The agent trusts the tools. The tools trust the agent. The data those tools return flows directly into the agent's context window, where it influences future decisions. There is no sandbox. There is no mandatory validation layer. There is a thin set of protocol-level hints — like destructiveHint, which signals whether a tool should trigger a user confirmation — but these are advisory, not enforced.

This architecture has a fundamental property that security engineers need to internalize: the attack surface is not just the tools themselves, it is everything those tools can read. If a tool fetches a web page, a database record, a pull request description, or a log file, that content enters the agent's context. If an attacker controls that content, they can influence the agent's behavior. This is prompt injection, and it is the master key that makes every other MCP vulnerability exploitable.


The Methodology

We approached this the same way a red team approaches an unfamiliar codebase: systematically, starting broad and narrowing to confirmed exploitability.

Phase 1 — Discovery and triage. We identified official MCP servers from high-value vendors: companies with enterprise customer bases, active bug bounty programs, and MCP implementations that touched sensitive operations. Database servers, CI/CD integrations, identity providers, infrastructure management tools. We cloned each repo and ran automated static analysis — semgrep with custom rules targeting MCP-specific patterns, bandit for Python targets, manual grep for credential handling, URL construction, and query parameterization.

Phase 2 — Pattern identification. Static analysis produces signal, not findings. We reviewed every flag manually, looking for patterns that would be exploitable in a realistic agent deployment. We specifically looked for: unsanitized parameters being interpolated into queries or commands, credential material being returned in tool responses, read-only flags that didn't actually restrict dangerous operations, and missing or incorrect destructiveHint annotations.

Phase 3 — Live verification. This is where many security research workflows stop short, and where we made a deliberate rule for ourselves: no advisory without a confirmed live PoC. We spun up local instances of every target — Docker containers for database servers, real accounts for cloud services, local npm installs for MCP framework libraries. Every finding was tested against a running instance before any disclosure was filed. One finding that looked strong on static analysis failed to reproduce on the current default configuration. We closed it rather than file a finding we couldn't prove.

Phase 4 — Disclosure. GHSA private reporting where available, MSRC portal for Microsoft targets, direct email for vendors without a formal channel. Every disclosure included the vulnerable code location, a reproduction script, and expected output.


The Vulnerability Classes

Across the servers we examined, the same classes of vulnerability appeared repeatedly. We describe them here as patterns, not as vendor-specific findings.

Pattern 1: The destructiveHint Mislabel

The MCP specification includes a destructiveHint field in tool definitions. When set to true, compliant MCP clients — Claude Desktop, Cursor, VS Code Copilot — are supposed to prompt the user before executing the tool. When set to false, the tool executes silently.

We found multiple instances where a tool that performs a genuinely destructive or sensitive operation was annotated with destructiveHint: false. In one case, the mislabeled tool was the only write operation in an entire codebase that creates executable code — every other write operation was correctly annotated. The inconsistency was not random noise. It was a specific tool, doing a specific sensitive thing, with the wrong annotation.

The exploitability of this pattern depends on prompt injection as a prerequisite. If an attacker can influence what content an LLM agent reads — through a malicious web page, a poisoned database record, a crafted pull request description — they can instruct the agent to call the mislabeled tool. Because destructiveHint: false, the MCP client never warns the user. The operation executes silently.

The fix is straightforward: audit every tool's destructiveHint annotation against what the tool actually does. Any tool that creates, modifies, or deletes data — or that triggers an action with real-world consequences — should be annotated true.

Pattern 2: The Read-Only Bypass

Several MCP servers expose a "read-only mode" — a configuration flag or runtime setting that is supposed to restrict the agent to non-destructive operations. The security model relies on this flag to make the server safe for deployment in contexts where the agent shouldn't be able to modify data.

We found multiple cases where the read-only flag did not restrict all dangerous operations. The common failure mode: the flag was implemented by blocking a specific list of write operations, rather than by allowing only a specific list of read operations. The difference matters enormously. A blocklist approach fails when there are operations that aren't writes in the traditional sense but still have dangerous effects — functions that execute arbitrary code, commands that flush entire databases, queries that exfiltrate sensitive data by design.

One particularly clean example: a Redis MCP server marked a command execution tool as readonly: true in its metadata. The tool accepted and executed EVAL (arbitrary Lua code execution) and FLUSHALL (destroys the entire database). Neither is a "write" in the key-value sense, but both are obviously destructive. The read-only flag provided false assurance to anyone who trusted it.

The correct implementation of read-only mode is an allowlist, not a blocklist. Define exactly which operations are permitted in read-only mode. Reject everything else.

Pattern 3: The Elicitation Bypass

The MCP protocol includes an elicitation mechanism — a way for the server to pause tool execution and ask the user a confirmation question. This is a more flexible version of destructiveHint: instead of just flagging a tool as destructive, the server can ask a specific question before proceeding.

We found an implementation where the elicitation function included a fallback: if the MCP client didn't support elicitation (which most clients don't, including Cursor and VS Code), the function returned true and proceeded anyway. The safety mechanism failed open silently. On the majority of MCP clients in production use, the confirmation never happened.

This is a subtle but important failure mode. The code appears to implement a safety check. It does implement a safety check — but only for clients that support the feature. For everyone else, it's a no-op that returns the permissive answer. A developer reading the code would see the elicitation call and reasonably conclude that dangerous operations are gated behind user confirmation. They would be wrong.

Pattern 4: Operator and Query Injection

Multiple database MCP servers accepted raw query parameters that were passed through to the underlying database engine with insufficient validation. The specific mechanisms varied by database: SQL injection via unparameterized query strings, NoSQL operator injection via unsanitized aggregation pipelines, GraphQL injection via string interpolation in query construction.

The NoSQL operator injection case was particularly interesting because it involved operators that execute server-side JavaScript — $where, $function, and $accumulator in MongoDB's aggregation framework. These operators don't just retrieve data; they execute arbitrary JavaScript in the database engine's context. A filter meant to block dangerous aggregation stages checked for $out and $merge (the write operators) but not for the JavaScript execution operators. The check demonstrated awareness that stage filtering was necessary — the wrong stages were filtered.

The GraphQL injection case involved a helper function that was used in some query paths but not others. One function supported parameterized variables; another didn't. A specific tool used the non-parameterized version, interpolating user input directly into the query string. The other tool using the parameterized version worked correctly. The inconsistency was invisible without reading both functions and tracing which one each tool called.

Pattern 5: Credential Exposure via Tool Response

We found at least one case where an MCP tool's stated purpose was to return an API credential to the LLM context. The tool description itself noted that this credential was "not needed" by the server. The credential was returned anyway, making it available to any prompt injection payload that triggered the tool call.

This is a design-level failure rather than an implementation bug. The tool should not exist. Credentials should not flow through the LLM context under any circumstances — they should be used by the server on the client's behalf, not returned to the agent. Any architecture that puts credentials in the LLM's context window should be treated as a potential exfiltration path.

Pattern 6: Spotlighting Coverage Gaps

Microsoft's research team published a technique called "spotlighting" — wrapping tool responses in XML delimiters that clearly mark data as untrusted content, separate from instructions. The idea is to make it harder for prompt injection payloads embedded in data to influence the agent's behavior. Microsoft explicitly recommends this technique in their published guidance on LLM security.

We examined a Microsoft-maintained MCP server and found that spotlighting was implemented in 3 of 91 tools — a 3.3% coverage rate. The 97% gap included exactly the tools most likely to contain attacker-controlled content: pull request descriptions, work item fields, wiki pages, code search results, comments. The tools that were protected were lower-risk read operations. The tools that were unprotected were the ones an attacker would target.

There is a particular irony in finding a spotlighting coverage gap in a server maintained by the team that published the spotlighting technique. It suggests that even when security guidance exists and is understood by the team, the operational challenge of applying it consistently across a large tool surface is significant.


What This Means for the Ecosystem

The pattern across these findings is not that individual developers made careless mistakes. The pattern is that MCP server development is happening faster than MCP security thinking, and the protocol itself does not make secure implementation the path of least resistance.

destructiveHint is advisory. Elicitation support is optional. There is no mandatory input validation layer. There is no standardized way to mark content as untrusted before it enters the agent's context. The protocol gives developers the building blocks for a secure implementation, but it does not prevent an insecure one.

Several things need to change at the ecosystem level:

Standardized security testing for MCP servers. Before an official MCP server ships, it should go through the same kind of review that would be applied to any API handling sensitive operations. The vulnerability classes described in this post are not exotic. They are the same classes that appear in any API security audit. Standard tooling exists to find them.

Mandatory PoC verification before disclosure. This is a lesson we learned ourselves during this research. Static analysis is hypothesis generation. Live verification is confirmation. A finding that looks like a critical vulnerability in source code may not be exploitable in the default configuration. File findings you can prove, not findings you believe.

Spotlighting as a default, not an optimization. Any tool that returns user-controlled content should wrap that content in untrusted-data delimiters. This should be the default behavior in MCP server frameworks, not a technique developers have to know about and apply manually.

Read-only mode as an allowlist. Any MCP server that exposes a read-only configuration should define read-only as an explicit allowlist of permitted operations, not a blocklist of prohibited ones.


What's Next

We are continuing this research. The advisories filed during this research are under coordinated disclosure. When the disclosure windows close — beginning in July 2026 — we will publish the full technical details: vendor names, CVE numbers, PoC scripts, and fix recommendations.

In the meantime, if you are operating an MCP server in a production environment, the questions worth asking are: Do you know which of your tools have incorrect destructiveHint annotations? Does your read-only mode use an allowlist or a blocklist? Does any tool return credential material in its response? Are the tools that read user-controlled content applying any form of untrusted-data marking?

These are not hard questions to answer. They are easy to overlook when you are moving fast.

AgentSentry by Akav Labs is a transparent MCP gateway that applies enforcement policies to agent tool calls before they reach your MCP servers. If you are interested in the research or want to discuss your MCP security posture, reach out at akavlabs@pm.me.


Akav Labs is a security research organization focused on AI agent security. The AgentSentry platform provides runtime protection for MCP deployments. All vendor disclosures in this research were handled under coordinated disclosure principles.

© 2026 Akav Labs — akav.io