CVE-2026-6566

Photo Gallery, Sliders, Proofing and Themes <= 4.2.0 - Insecure Direct Object Reference to Authenticated (Subscriber+) Image Deletion via REST API

mediumAuthorization Bypass Through User-Controlled Key
4.3
CVSS Score
4.3
CVSS Score
medium
Severity
4.2.1
Patched in
1d
Time to patch

Description

The Photo Gallery, Sliders, Proofing and Themes – NextGEN Gallery plugin for WordPress is vulnerable to Insecure Direct Object Reference in versions up to and including 4.2.0. This is due to insufficient object-level authorization in the image deletion REST flow where the permission callback for DELETE /imagely/v1/images/{id} only checks 'NextGEN Manage gallery' permissions and does not enforce gallery ownership or 'NextGEN Manage others gallery' permissions. This makes it possible for authenticated attackers, with Subscriber-level privileges and 'NextGEN Manage gallery' capability, to delete gallery images belonging to other users as well as their associated image files from disk when deleteImg is enabled (default).

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<=4.2.0
PublishedMay 19, 2026
Last updatedMay 20, 2026
Affected pluginnextgen-gallery

What Changed in the Fix

Changes introduced in v4.2.1

Loading patch diff...

Source Code

WordPress.org SVN
Research Plan
Unverified

# Exploitation Research Plan - CVE-2026-6566 ## 1. Vulnerability Summary The **NextGEN Gallery** plugin (versions <= 4.2.0) contains an **Insecure Direct Object Reference (IDOR)** vulnerability in its REST API implementation for image deletion. Specifically, the endpoint `DELETE /imagely/v1/images/…

Show full research plan

Exploitation Research Plan - CVE-2026-6566

1. Vulnerability Summary

The NextGEN Gallery plugin (versions <= 4.2.0) contains an Insecure Direct Object Reference (IDOR) vulnerability in its REST API implementation for image deletion. Specifically, the endpoint DELETE /imagely/v1/images/{id} fails to perform proper object-level authorization. While it checks if a user has the general NextGEN Manage gallery capability, it does not verify if the user owns the gallery containing the image or possesses the higher-privilege NextGEN Manage others gallery capability. This allows any authenticated user with the NextGEN Manage gallery capability (which can be assigned to Subscriber-level roles via plugin settings) to delete images belonging to any other user.

2. Attack Vector Analysis

  • Endpoint: /wp-json/imagely/v1/images/{id}
  • HTTP Method: DELETE (or POST with _method=DELETE / X-HTTP-Method-Override: DELETE)
  • Authentication: Authenticated. Requires a user with the NextGEN Manage gallery capability.
  • Payload Parameter: {id} in the URL represents the image ID in the {prefix}_ngg_pictures table.
  • Preconditions:
    1. The attacker must have a Subscriber account.
    2. The "NextGEN Gallery" -> "Other Options" -> "Roles & Capabilities" must be configured to allow the Subscriber role the NextGEN Manage gallery capability (a common configuration for multi-user sites).
    3. deleteImg option is enabled (default behavior), which causes the image files to be unlinked from the filesystem.

3. Code Flow (Inferred)

Based on NextGEN's module architecture and the vulnerability description:

  1. Route Registration: The plugin registers the route imagely/v1/images/(?P<id>[\d]+) using register_rest_route.
  2. Permission Callback: The permission_callback for the DELETE method likely calls a function that only checks:
    return current_user_can('NextGEN Manage gallery');
  3. Execution Callback: The controller's deletion method takes the {id}, retrieves the image record from the database, and proceeds to delete it:
    • It fetches the image object via the NextGEN DataMapper (e.g., \Imagely\NGG\DataMappers\Image::get_instance()->find($id)).
    • It fails to compare the image's galleryid ownership against the current_user_id.
    • It calls the storage deletion method (e.g., $storage->delete_image($id)), which removes the database entry and unlinks the file from wp-content/gallery/.

4. Nonce Acquisition Strategy

The REST API requires a standard WordPress REST nonce (wp_rest).

  1. Shortcode/Page Setup: NextGEN's admin dashboard or any page where the NextGEN "Manage Galleries" interface is loaded will contain the necessary nonce.
  2. Strategy:
    • Log in as the Subscriber.
    • Access the NextGEN Dashboard (if available) or any admin page.
    • The plugin relies on the core WordPress REST API settings.
  3. Extraction:
    • Use browser_eval to extract the nonce from the wpApiSettings global object provided by WordPress core when REST-enabled scripts are loaded.
    • JavaScript: window.wpApiSettings.nonce

5. Exploitation Strategy

Step 1: Target Identification

Determine the ID of an image belonging to another user (e.g., the Administrator).

  • This can often be found by inspecting the frontend of a gallery (NextGEN image IDs are frequently exposed in HTML attributes or lightbox data).

Step 2: Request Construction

Perform a DELETE request using the http_request tool.

Request Details:

  • URL: http://localhost:8080/wp-json/imagely/v1/images/{TARGET_IMAGE_ID}
  • Method: DELETE
  • Headers:
    • X-WP-Nonce: [EXTRACTED_NONCE]
    • Content-Type: application/json
    • Cookie: [SUBSCRIBER_COOKIES]

Step 3: Execution

If the server returns a 200 OK or 204 No Content, the image has been deleted despite it not belonging to the Subscriber.

6. Test Data Setup

  1. Users:
    • User A: Administrator (ID 1).
    • User B: Subscriber (ID 2).
  2. Capability Setup (via WP-CLI):
    • Grant the required capability to the subscriber role (simulating a common plugin config):
      wp ngg capabilities add subscriber "NextGEN Manage gallery"
  3. Content Creation:
    • User A (Admin) creates a gallery and uploads an image victim.jpg.
    • Record the image ID: wp db query "SELECT pid FROM wp_ngg_pictures WHERE filename='victim.jpg'"
  4. Attacker Context:
    • User B (Subscriber) creates their own gallery to ensure they have an active session and the capability works.

7. Expected Results

  • Success: The REST API returns a success response. The image record is removed from the {prefix}_ngg_pictures table, and the file wp-content/gallery/{gallery_name}/victim.jpg is deleted from the disk.
  • Failure: The REST API returns a 403 Forbidden or 401 Unauthorized.

8. Verification Steps

  1. Database Check:
    wp db query "SELECT * FROM wp_ngg_pictures WHERE pid = {TARGET_IMAGE_ID}"
    (Should return no results).
  2. Filesystem Check:
    ls /var/www/html/wp-content/gallery/{gallery_name}/victim.jpg
    (Should return "No such file or directory").

9. Alternative Approaches

If the DELETE method is blocked by server configuration (e.g., some WAFs or specific Nginx configs):

  • Use POST with the method override header:
    POST /wp-json/imagely/v1/images/{id} HTTP/1.1
    X-HTTP-Method-Override: DELETE
    X-WP-Nonce: ...
    
  • Use POST with the _method parameter:
    POST /wp-json/imagely/v1/images/{id}?_method=DELETE HTTP/1.1
    X-WP-Nonce: ...
    
Research Findings
Static analysis — not yet PoC-verified

Summary

The NextGEN Gallery plugin for WordPress is vulnerable to an Insecure Direct Object Reference (IDOR) via its REST API in versions up to and including 4.2.0. Authenticated users with the 'NextGEN Manage gallery' capability can delete images belonging to any user because the image deletion endpoint fails to verify gallery ownership or 'manage others' permissions.

Security Fix

diff -ru /home/deploy/wp-safety.org/data/plugin-versions/nextgen-gallery/4.2.0/adminApp/build/dependencies.php /home/deploy/wp-safety.org/data/plugin-versions/nextgen-gallery/4.2.1/adminApp/build/dependencies.php
--- /home/deploy/wp-safety.org/data/plugin-versions/nextgen-gallery/4.2.0/adminApp/build/dependencies.php	2026-04-24 16:23:10.000000000 +0000
+++ /home/deploy/wp-safety.org/data/plugin-versions/nextgen-gallery/4.2.1/adminApp/build/dependencies.php	2026-05-15 21:15:30.000000000 +0000
@@ -1 +1 @@
-<?php return array('dependencies' => array('react', 'react-dom', 'react-jsx-runtime', 'wp-api-fetch', 'wp-components', 'wp-data', 'wp-element', 'wp-i18n'), 'version' => '713cb6f59506e3d395e8');
+<?php return array('dependencies' => array('react', 'react-dom', 'react-jsx-runtime', 'wp-api-fetch', 'wp-components', 'wp-data', 'wp-element', 'wp-i18n'), 'version' => 'f7afa128be1833048fd9');
diff -ru /home/deploy/wp-safety.org/data/plugin-versions/nextgen-gallery/4.2.0/adminApp/build/index.min.js /home/deploy/wp-safety.org/data/plugin-versions/nextgen-gallery/4.2.1/adminApp/build/index.min.js
--- /home/deploy/wp-safety.org/data/plugin-versions/nextgen-gallery/4.2.0/adminApp/build/index.min.js	2026-04-24 16:23:10.000000000 +0000
+++ /home/deploy/wp-safety.org/data/plugin-versions/nextgen-gallery/4.2.1/adminApp/build/index.min.js	2026-05-15 21:15:30.000000000 +0000
@@ -1,2 +1,2 @@
 /*! For license information please see index.min.js.LICENSE.txt */
-(()=>{var e,t,n,r,a={338:(e,t,n)=>{"use strict";var r=n(795);t.H=r.createRoot,r.hydrateRoot},93:function(e,t,n){var r;r=e=>(()=>{"use strict";var t={899:t=>{t.exports=e}},n={};... (truncated)

Exploit Outline

The exploit target the REST API endpoint `DELETE /wp-json/imagely/v1/images/{id}`. An attacker requires authentication with the 'NextGEN Manage gallery' capability, which can be granted to Subscriber-level users in the plugin's settings. 1. Log in as an authorized user (e.g., Subscriber with the management capability). 2. Obtain the standard WordPress REST API nonce (`wp_rest`) from the admin dashboard (e.g., from the `wpApiSettings.nonce` global object). 3. Identify the target image ID (`pid`) of an image belonging to another user (often visible in frontend HTML or lightbox metadata). 4. Execute a `DELETE` request to `/wp-json/imagely/v1/images/{TARGET_ID}` with the `X-WP-Nonce` header. 5. The plugin's failure to check for 'NextGEN Manage others gallery' or gallery ownership allows the request to succeed, resulting in the removal of the image record from the database and the deletion of the associated file from the filesystem.

Check if your site is affected.

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