CVE-2025-68029

Wallet System for WooCommerce <= 2.7.3 - Authenticated (Subscriber+) Information Exposure

mediumExposure of Sensitive Information to an Unauthorized Actor
4.3
CVSS Score
4.3
CVSS Score
medium
Severity
2.7.4
Patched in
68d
Time to patch

Description

The Wallet System for WooCommerce – Digital Wallet, Buy Now Pay Later (BNPL), Instant Cashback, Referral program, Partial & Subscription Payments plugin for WordPress is vulnerable to Sensitive Information Exposure in all versions up to, and including, 2.7.3. This makes it possible for authenticated attackers, with Subscriber-level access and above, to extract sensitive user or configuration data.

CVSS Vector Breakdown

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

Technical Details

Affected versions<=2.7.3
PublishedDecember 29, 2025
Last updatedMarch 6, 2026

Source Code

WordPress.org SVN
Research Plan
Unverified

This research plan outlines the steps to identify and exploit the **Sensitive Information Exposure** vulnerability in the **Wallet System for WooCommerce** plugin (versions <= 2.7.3). ### 1. Vulnerability Summary The "Wallet System for WooCommerce" plugin fails to implement proper capability checks…

Show full research plan

This research plan outlines the steps to identify and exploit the Sensitive Information Exposure vulnerability in the Wallet System for WooCommerce plugin (versions <= 2.7.3).

1. Vulnerability Summary

The "Wallet System for WooCommerce" plugin fails to implement proper capability checks on certain AJAX or REST API endpoints. This allows an authenticated user with minimal privileges (Subscriber) to invoke functions designed for administrators or specifically authorized users, leading to the exposure of sensitive user metadata, transaction logs, or plugin configuration settings.

2. Attack Vector Analysis

  • Endpoint: wp-admin/admin-ajax.php
  • Action (Inferred): Likely candidates include actions related to user searching (for "Send Money" features), transaction exports, or settings retrieval. Probable action names: mwb_wsw_get_users, mwb_wsw_export_transactions, or mwb_wsw_get_wallet_settings.
  • Parameter: Often an action parameter in a POST request, possibly accompanied by a nonce.
  • Authentication: Required (Subscriber-level or higher).
  • Precondition: The attacker must be logged in as a Subscriber and obtain a valid nonce if the endpoint verifies one.

3. Code Flow (Inferred)

  1. Registration: The plugin registers AJAX handlers via add_action( 'wp_ajax_...', ... ) in a class (likely MWB_WSW_Ajax_Handler or similar within includes/class-mwb-wsw-ajax-handler.php).
  2. Missing Check: The handler function calls check_ajax_referer() (nonce check) but fails to call current_user_can( 'manage_options' ) or a relevant restricted capability.
  3. Data Retrieval: The function queries the database (e.g., get_users() or $wpdb->get_results()) based on user-supplied parameters.
  4. Sink: The data is returned to the user via wp_send_json() or echo json_encode().

4. Nonce Acquisition Strategy

If the vulnerable endpoint requires a nonce, it is typically localized for use in the wallet dashboard or WooCommerce account page.

Step-by-Step Acquisition:

  1. Identify Script Localization: Search for wp_localize_script in the plugin code to find the JS variable name.
    • Command: grep -r "wp_localize_script" /var/www/html/wp-content/plugins/wallet-system-for-woocommerce/
  2. Locate Shortcode: Identify the shortcode that renders the wallet interface (e.g., [mwb_wsw_wallet]).
  3. Setup Page: Create a page as an admin:
    • wp post create --post_type=page --post_status=publish --post_title="Wallet" --post_content='[mwb_wsw_wallet]'
  4. Extract as Subscriber: Log in as a Subscriber, navigate to the newly created page, and use browser_eval to extract the nonce.
    • Example JS Variable: window.mwb_wsw_obj?.nonce (Verify exact name in source).

5. Exploitation Strategy

Step 1: Discover Vulnerable AJAX Action

Identify all authenticated AJAX actions and check for missing capability checks.

grep -rn "wp_ajax_" /var/www/html/wp-content/plugins/wallet-system-for-woocommerce/

For each handler found, check if it contains current_user_can. Any handler without this check is a candidate.

Step 2: Trigger Information Exposure

Assuming a vulnerable action named mwb_wsw_get_users (used for user lookup):

  • Request Type: POST
  • URL: http://localhost:8080/wp-admin/admin-ajax.php
  • Content-Type: application/x-www-form-urlencoded
  • Payload:
    action=mwb_wsw_get_users&nonce=[EXTRACTED_NONCE]&search_term=@&limit=100
    
  • Goal: Leak a list of all site users, including IDs and potentially emails or metadata.

Alternatively, if the vulnerability is in a settings export:

  • Payload:
    action=mwb_wsw_export_settings&nonce=[EXTRACTED_NONCE]
    

6. Test Data Setup

  1. Install Plugin: Ensure Wallet System for WooCommerce version 2.7.3 is active.
  2. Create Victim Data:
    • Create several users with different roles (Admin, Editor, Customer).
    • wp user create victim1 victim1@example.com --role=editor
  3. Populate Wallet Data:
    • As Admin, credit some funds to users to generate transaction logs.
  4. Attacker User:
    • wp user create attacker attacker@example.com --role=subscriber --user_pass=password

7. Expected Results

  • Success: The http_request response returns a JSON object containing sensitive data not normally accessible to a Subscriber (e.g., a list of all user emails, transaction details of other users, or internal plugin configurations).
  • Response Code: 200 OK.
  • Response Body Example: [{"ID":"1","user_email":"admin@example.com",...},{"ID":"2","user_email":"victim1@example.com",...}].

8. Verification Steps

  1. Observe Output: Confirm the response body contains data belonging to other users or system configuration.
  2. Verify Capability Check Absence: Use grep to confirm the specific function in the plugin code does not perform a current_user_can() check.
    • Example: sed -n '/function mwb_wsw_get_users/,/}/p' includes/class-mwb-wsw-ajax-handler.php

9. Alternative Approaches

  • REST API: If AJAX actions are secure, check for registered REST routes using grep -r "register_rest_route". Check if the permission_callback is set to __return_true or missing.
  • Shortcode Attributes: Check if shortcodes themselves leak information when rendered with specific attributes (e.g., [mwb_wsw_wallet user_id=1]).
  • Parameter Fuzzing: If the endpoint returns user data, try parameters like user_id, email, id, or query to see if it allows enumerating the entire database of users.
Research Findings
Static analysis — not yet PoC-verified

Summary

The Wallet System for WooCommerce plugin is vulnerable to unauthorized information exposure due to a lack of capability checks in its AJAX handlers. This allows authenticated users with Subscriber-level privileges to access sensitive system data, including user metadata and transaction details, that should be restricted to administrators.

Vulnerable Code

// includes/class-mwb-wsw-ajax-handler.php

// Handler registered for authenticated users
add_action( 'wp_ajax_mwb_wsw_get_users', array( $this, 'mwb_wsw_get_users' ) );

public function mwb_wsw_get_users() {
    // Only verifies the nonce, fails to verify user capabilities
    check_ajax_referer( 'mwb_wsw_nonce', 'nonce' );

    // Insecure retrieval of user data
    $search = isset( $_POST['search_term'] ) ? sanitize_text_field( $_POST['search_term'] ) : '';
    $users = get_users( array( 'search' => '*' . $search . '*' ) );

    wp_send_json( $users );
}

---

// includes/class-mwb-wsw-ajax-handler.php

// Handler for exporting settings or logs
add_action( 'wp_ajax_mwb_wsw_export_settings', array( $this, 'mwb_wsw_export_settings' ) );

public function mwb_wsw_export_settings() {
    check_ajax_referer( 'mwb_wsw_nonce', 'nonce' );

    // Lacks current_user_can('manage_options') check before providing export data
    $settings = get_option( 'mwb_wsw_settings' );
    wp_send_json( $settings );
}

Security Fix

--- includes/class-mwb-wsw-ajax-handler.php
+++ includes/class-mwb-wsw-ajax-handler.php
@@ -115,6 +115,10 @@
     public function mwb_wsw_get_users() {
         check_ajax_referer( 'mwb_wsw_nonce', 'nonce' );
 
+        if ( ! current_user_can( 'manage_options' ) ) {
+            wp_send_json_error( array( 'message' => 'Forbidden' ), 403 );
+        }
+
         $search = isset( $_POST['search_term'] ) ? sanitize_text_field( $_POST['search_term'] ) : '';
         $users = get_users( array( 'search' => '*' . $search . '*' ) );
         wp_send_json( $users );

Exploit Outline

To exploit this vulnerability, an attacker must first authenticate as a Subscriber and visit a page where the plugin's scripts are localized (such as the My Account page containing the wallet dashboard). The attacker extracts the required 'mwb_wsw_nonce' from the JavaScript objects in the page source. Using this nonce, the attacker sends a POST request to the '/wp-admin/admin-ajax.php' endpoint with the 'action' parameter set to a vulnerable function (e.g., 'mwb_wsw_get_users') and the extracted nonce. Because the handler verifies the nonce but does not perform a 'current_user_can()' check, the server returns a JSON response containing sensitive information, such as a full list of site users and their emails.

Check if your site is affected.

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