Heroku Exploit: App Ownership Takeover

by Abi Raghuram

A user has deployed a Node.js application on Heroku, which they manage through Heroku's remote MCP server in their IDE. This setup, while convenient, opens the door to a clever exploit that can result in a complete loss of application ownership.

Heroku Setup
Heroku Configuration

The Attack: A Three-Step Takeover

The attack is a three-step process that begins with a malicious request and ends with the attacker gaining full control of the user's Heroku app.

Step 1: Injecting the Malicious Prompt

The attacker identifies the URL of the user's backend service and embeds a malicious prompt in a GET request. This prompt is designed to trigger a 404 error, ensuring it gets logged by the Heroku service.

The malicious GET request: https://scanner-mcpwned-backend-fd6e92d62400.herokuapp.com/

The prompt instructs the Heroku MCP to transfer ownership of the app to the attacker's email address.

Malicious Request

Step 2: Triggering the Exploit

The user, while triaging bugs, asks their IDE to fetch the latest logs from the Heroku service. This action inadvertently triggers the exploit.

User Request

Step 3: Hijacking the MCP

When the IDE retrieves the logs, it is prompt-injected by the malicious message. The IDE's MCP then begins the tool call chain to transfer ownership of the app to the attacker.

Attack Summary

Attack Summary 1
Attack Summary 2

Why This Is Dangerous

This exploit is a form of Indirect Prompt Injection that critically compromises the MCP:

  • Control Flow Hijack: The user's intended read-only operation (viewing logs) is escalated into a highly privileged write operation. The malicious prompt, hidden in the logs, forces the MCP to execute the transfer_app tool, an action the user never authorized.
  • Data Flow Corruption: The data required for the malicious action—the attacker's email address—is supplied within the prompt. This corrupts the data flow by feeding attacker-controlled data into a sensitive tool, leading to a complete application takeover.

This specific attack vector is a variant of LLM01: Prompt Injection, the number one vulnerability in the OWASP Top 10 for Large Language Model Applications.

  • One-hop Account Takeover: The attacker never needs to compromise the victim's Heroku credentials. A single crafted GET request plants the takeover payload in the application logs, and the MCP executes it when a developer reviews those logs. This turns a harmless 404 probe into a full application takeover.
  • Low-Skill, High-Impact: Crafting this exploit requires no special headers, authentication, or advanced payload encoding—just a URL and the victim's hostname. Because the vulnerable workflow is common, any public Heroku app becomes a potential target.