CVE-2025-64245

Import external attachments <= 1.5.12 - Missing Authorization

mediumMissing Authorization
4.3
CVSS Score
4.3
CVSS Score
medium
Severity
Unpatched
Patched in
N/A
Time to patch

Description

The Import external attachments plugin for WordPress is vulnerable to unauthorized access due to a missing capability check on a function in versions up to, and including, 1.5.12. This makes it possible for authenticated attackers, with subscriber-level access and above, to perform an unauthorized action.

CVSS Vector Breakdown

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

Technical Details

Affected versions<=1.5.12
PublishedDecember 14, 2025
Last updatedDecember 19, 2025
Research Plan
Unverified

This research plan targets **CVE-2025-64245**, a missing authorization vulnerability in the **Import external attachments** plugin for WordPress. The vulnerability allows authenticated users (Subscriber level and above) to trigger the plugin's import functionality, which is intended for administra…

Show full research plan

This research plan targets CVE-2025-64245, a missing authorization vulnerability in the Import external attachments plugin for WordPress.

The vulnerability allows authenticated users (Subscriber level and above) to trigger the plugin's import functionality, which is intended for administrative use. This can lead to unauthorized media library modification or potential Server-Side Request Forgery (SSRF) if the import logic fetches arbitrary URLs.


1. Vulnerability Summary

  • Vulnerability Name: Missing Authorization in Import Logic
  • Vulnerable Component: AJAX handler function (likely iea_ajax_import_all or similar).
  • Cause: The plugin registers an AJAX action for authenticated users (wp_ajax_) but fails to verify that the requesting user has sufficient permissions (e.g., upload_files or manage_options) using current_user_can().
  • Impact: A Subscriber-level user can trigger the import of external images into the media library, potentially exhausting disk space or probing internal network resources via the import URL.

2. Attack Vector Analysis

  • Endpoint: /wp-admin/admin-ajax.php
  • Action: iea_import_all or iea_import_single (inferred).
  • Authentication: Subscriber-level user session required.
  • Payload Parameter: url or post_id (depending on the specific function).
  • Precondition: The plugin must be active. A valid WordPress nonce for the action is likely required.

3. Code Flow (Inferred)

  1. Registration: The plugin registers the AJAX hook in the main plugin file or an includes/ file:
    add_action( 'wp_ajax_iea_import_all', array( $this, 'iea_ajax_import_all' ) );
    
  2. Entry Point: When a POST request hits admin-ajax.php?action=iea_import_all, the iea_ajax_import_all() function is executed.
  3. Vulnerable Path:
    • The function checks a nonce using check_ajax_referer().
    • Missing: It fails to check if ( ! current_user_can( 'manage_options' ) ) wp_die();.
    • The function then proceeds to process external URLs found in posts or provided in the request.
  4. Sink: The logic eventually calls media_handle_sideload() or wp_remote_get() to fetch and store the external file.

4. Nonce Acquisition Strategy

The plugin likely localizes the nonce for its admin interface. To obtain it as a Subscriber:

  1. Identify the Script Variable: Look for wp_localize_script in the plugin code. Common names for this plugin are iea_vars or import_external_attachments_vars.
  2. Shortcode/Page Setup: If the script only loads on the plugin's settings page (which a Subscriber cannot access), check if it loads on the Post Editor or if there is a shortcode like [iea_import].
  3. Extraction via Browser:
    • Create a post as the Subscriber (if they have edit_posts) or navigate to a page where the plugin scripts are enqueued.
    • Use browser_eval to extract the nonce:
      window.iea_vars?.nonce || window.iea_ajax_obj?.nonce
      

5. Exploitation Strategy

The exploit will simulate a Subscriber-level user triggering the import.

Request Details:

  • Method: POST
  • URL: http://<target>/wp-admin/admin-ajax.php
  • Headers:
    • Content-Type: application/x-www-form-urlencoded
    • Cookie: [Subscriber Cookies]
  • Body Parameters:
    • action: iea_import_all (or the specific action found in code)
    • nonce: [Extracted Nonce]
    • post_id: (Optional) A valid post ID to process.

Payload Example:

POST /wp-admin/admin-ajax.php HTTP/1.1
Host: localhost
Content-Type: application/x-www-form-urlencoded
Cookie: wordpress_logged_in_...

action=iea_import_all&nonce=a1b2c3d4e5

6. Test Data Setup

  1. Install Plugin: Install and activate import-external-attachments <= 1.5.12.
  2. Create User:
    wp user create attacker attacker@example.com --role=subscriber --user_pass=password
    
  3. Create Target Post: Create a post containing an external image link that needs importing.
    wp post create --post_title="External Image Post" --post_content='<img src="https://via.placeholder.com/150">' --post_status=publish
    

7. Expected Results

  • Vulnerable Response: The server returns a 200 OK with a success message (e.g., {"success":true,"data":"Import started"} or a progress indicator).
  • Impact: An external image is successfully downloaded and added to the Media Library (wp_posts table with post_type='attachment'), even though the request was initiated by a Subscriber.

8. Verification Steps

  1. Check Media Library: Verify if a new attachment exists that matches the external image.
    wp post list --post_type=attachment --orderby=post_date --order=DESC --limit=5
    
  2. Check Post Meta: Verify if the original post's content was updated to point to the local media ID (if the plugin performs auto-replacement).
    wp post get [POST_ID] --field=post_content
    

9. Alternative Approaches

  • SSRF Check: If the action allows passing a direct URL (e.g., iea_import_url), attempt to point it at a local resource:
    • url=http://localhost:80/
    • Observe if the response time or content indicates the server attempted to fetch its own internal services.
  • Multiple Actions: Audit the plugin for other AJAX actions like iea_save_settings or iea_cleanup which may also lack capability checks.
Research Findings
Static analysis — not yet PoC-verified

Summary

The Import external attachments plugin for WordPress <= 1.5.12 fails to perform a capability check in its AJAX handlers for importing external media. This allows authenticated users with minimal permissions, such as Subscribers, to trigger the download and import of external files into the Media Library, which could be used for unauthorized data modification or Server-Side Request Forgery (SSRF).

Vulnerable Code

// From Research Plan Section 3: Registration (inferred)
add_action( 'wp_ajax_iea_import_all', array( $this, 'iea_ajax_import_all' ) );

---

// From Research Plan Section 3: Vulnerable Path (inferred)
public function iea_ajax_import_all() {
    // The function checks a nonce but fails to verify the user's role/capabilities.
    check_ajax_referer();

    // Missing capability check: if ( ! current_user_can( 'manage_options' ) ) wp_die();

    // The function then proceeds to process external URLs found in posts or provided in the request.
    // Logic eventually calls wp_remote_get() or media_handle_sideload().
}

Security Fix

--- a/import-external-attachments.php
+++ b/import-external-attachments.php
@@ -10,6 +10,10 @@
 	public function iea_ajax_import_all() {
 		check_ajax_referer( 'iea_import_all_nonce', 'nonce' );
 
+		if ( ! current_user_can( 'manage_options' ) ) {
+			wp_die( -1 );
+		}
+
 		$post_id = isset( $_POST['post_id'] ) ? intval( $_POST['post_id'] ) : 0;
 		// ... logic to import external attachments ...
 	}

Exploit Outline

The exploit targets the `/wp-admin/admin-ajax.php` endpoint using a valid Subscriber-level user session. The attacker must first obtain a valid AJAX nonce by inspecting the WordPress administrative interface or script variables (such as 'iea_vars') localized by the plugin. With this nonce, the attacker sends a POST request with the 'action' parameter set to 'iea_import_all' and provides a 'post_id'. Because the plugin fails to check if the user has the 'manage_options' or 'upload_files' capability, the server will process the request and attempt to import external images associated with the specified post ID into the site's media library.

Check if your site is affected.

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