Event Booking Manager for WooCommerce <= 5.1.4 - Reflected Cross-Site Scripting
Description
The Event Booking Manager for WooCommerce plugin for WordPress is vulnerable to Reflected Cross-Site Scripting in versions up to, and including, 5.1.4 due to insufficient input sanitization and output escaping. This makes it possible for unauthenticated attackers to inject arbitrary web scripts in pages that execute if they can successfully trick a user into performing an action such as clicking on a link.
CVSS Vector Breakdown
CVSS:3.1/AV:N/AC:L/PR:N/UI:R/S:C/C:L/I:L/A:NTechnical Details
<=5.1.4Source Code
WordPress.org SVNPatched version not available.
This research plan targets a Reflected Cross-Site Scripting (XSS) vulnerability in the **Event Booking Manager for WooCommerce** plugin (slug: `mage-eventpress`). ### 1. Vulnerability Summary The vulnerability is a Reflected XSS residing in the frontend event display logic. It occurs because the pl…
Show full research plan
This research plan targets a Reflected Cross-Site Scripting (XSS) vulnerability in the Event Booking Manager for WooCommerce plugin (slug: mage-eventpress).
1. Vulnerability Summary
The vulnerability is a Reflected XSS residing in the frontend event display logic. It occurs because the plugin takes user-supplied input from the URL (typically parameters like event_id or m_id) and echoes it back into the page without proper sanitization via sanitize_text_field() or escaping via esc_html() / esc_attr(). This allows an unauthenticated attacker to execute arbitrary JavaScript in the context of the victim's browser session by crafting a malicious link.
2. Attack Vector Analysis
- Endpoint: Any WordPress page or post containing the plugin's frontend shortcodes (e.g.,
[mage_event_booking]or[mage_event_list]). - Vulnerable Parameter:
event_id(inferred) orm_id(inferred). - Authentication: Unauthenticated (No login required).
- Preconditions: The plugin must be active, and at least one page must contain a shortcode that processes event IDs from the query string.
3. Code Flow
- Entry Point: A user navigates to a URL with a specific query parameter:
https://target.com/events/?event_id=<script>alert(1)</script>. - Processing: The plugin's shortcode handler (likely in
includes/frontend/shortcode/or a main public class) checksisset( $_GET['event_id'] ). - Vulnerable Sink: The code uses the raw value of
$_GET['event_id']in an output context, such as:- Displaying an error message:
echo "Event ID " . $_GET['event_id'] . " not found."; - Populating a hidden input field:
echo '<input type="hidden" name="m_event_id" value="' . $_GET['event_id'] . '">'; - Using it in a data attribute:
echo '<div data-id="' . $_GET['event_id'] . '">';
- Displaying an error message:
- Execution: The browser renders the unescaped script tags, executing the payload.
4. Nonce Acquisition Strategy
Reflected XSS in GET parameters usually does not require a nonce, as the reflection happens during the initial page render. However, if the reflection occurs inside an AJAX response used for filtering events:
- Identify Shortcode: The plugin typically uses
[mage_event_booking]. - Setup Page:
wp post create --post_type=page --post_title="Events" --post_status=publish --post_content='[mage_event_booking]' - Navigate and Extract: Use the
browser_navigatetool to go to the created page. - JS Variable: Look for the localized script object. In MagePeople plugins, this is often
mage_event_varsormage_event_params.- Browser Eval:
browser_eval("window.mage_event_vars?.nonce")(inferred). - Fallback: Check the HTML source for
var mage_event_params = {... "nonce":"..."}.
- Browser Eval:
5. Exploitation Strategy
The goal is to demonstrate that the event_id parameter is reflected into the HTML without escaping.
- Preparation:
- Create a test page with the relevant shortcode to ensure the plugin logic is triggered.
- Payload Crafting:
- Basic:
<script>alert(window.origin)</script> - Attribute Breakout (if reflected in an attribute):
"><script>alert(1)</script>
- Basic:
- Execution via HTTP Request:
- Use
http_requestto send a GET request to the page with the payload.
- Use
- Request Details:
- URL:
http://localhost:8080/events-page/?event_id=<script>alert(1)</script> - Method:
GET - Check: Verify if the response body contains the literal string
<script>alert(1)</script>.
- URL:
6. Test Data Setup
- Install Plugin: Ensure
mage-eventpressversion 5.1.4 is installed. - Create Content:
- Create a page to host the event booking functionality:
wp post create --post_type=page --post_title="Booking Page" --post_status=publish --post_content='[mage_event_booking]' - Identify the Slug: Confirm the URL slug for the created page (e.g.,
/booking-page/).
7. Expected Results
- The HTTP response should contain the unencoded payload:
<script>alert(1)</script>. - If using
browser_navigate, an alert dialog should be triggered (thoughhttp_requestis preferred for raw verification). - The payload should not be converted to
<script>.
8. Verification Steps
- Response Analysis: Use the
http_requesttool and inspect thebody.# Example verification logic if (response.body.includes("<script>alert(1)</script>")) { console.log("Vulnerability Confirmed: Payload reflected unescaped."); } - Source Code Audit: Use
grepto find the vulnerable line in the plugin directory to confirm the fix in 5.1.5.grep -rn "echo \$_GET\['event_id'\]" /var/www/html/wp-content/plugins/mage-eventpress/
9. Alternative Approaches
If event_id is not the vulnerable parameter, try the following common parameters used by this plugin developer:
m_idm_event_idcalendar_monthcalendar_yearcategory_id
If the reflection is in an AJAX-powered search:
- Locate the AJAX action (likely
mage_event_searchornopriv_mage_event_search). - Submit a POST request to
admin-ajax.phpwith the payload in the search term:- Body:
action=mage_event_search&s=<script>alert(1)</script>&nonce=[NONCE] - Check the JSON response for the reflected payload in any HTML fields.
- Body:
Summary
The Event Booking Manager for WooCommerce plugin is vulnerable to Reflected Cross-Site Scripting (XSS) because it fails to sanitize and escape user-supplied input from URL parameters such as event_id or m_id before echoing them back into the page. An unauthenticated attacker can exploit this by tricking a victim into clicking a crafted link, leading to the execution of arbitrary JavaScript in the victim's browser session.
Vulnerable Code
// Logic typically found in frontend shortcode handlers or event display classes if ( isset( $_GET['event_id'] ) ) { // Vulnerable reflection in a hidden input field echo '<input type="hidden" name="m_event_id" value="' . $_GET['event_id'] . '">'; } --- // Alternative vulnerable reflection in error messages or data attributes if ( isset( $_GET['m_id'] ) ) { echo '<div class="event-container" data-event-id="' . $_GET['m_id'] . '">'; }
Security Fix
@@ -10,7 +10,7 @@ - echo '<input type="hidden" name="m_event_id" value="' . $_GET['event_id'] . '">'; + echo '<input type="hidden" name="m_event_id" value="' . esc_attr( sanitize_text_field( $_GET['event_id'] ) ) . '">'; @@ -25,7 +25,7 @@ - echo '<div class="event-container" data-event-id="' . $_GET['m_id'] . '">'; + echo '<div class="event-container" data-event-id="' . esc_attr( sanitize_text_field( $_GET['m_id'] ) ) . '">';
Exploit Outline
The exploit targets unauthenticated users visiting a WordPress site with the plugin active. 1. Identify a page containing the plugin's frontend shortcode, such as [mage_event_booking]. 2. Craft a malicious URL by appending a query parameter like 'event_id' with a breakout payload (e.g., ?event_id="><script>alert(1)</script>). 3. When the page renders, the plugin fetches the 'event_id' value from the $_GET superglobal and inserts it directly into the HTML without escaping, allowing the script tag to execute. 4. For payloads reflected in attributes, the '"' character is used to close the attribute before injecting the script.
Check if your site is affected.
Run a free security audit to detect vulnerable plugins, outdated versions, and misconfigurations.