Awesome Hotel Booking <= 1.0.3 - Incorrect Authorization to Unauthenticated Arbitrary Booking Modification
Description
The Awesome Hotel Booking plugin for WordPress is vulnerable to unauthorized modification of data due to incorrect authorization in the room-single.php shortcode handler in all versions up to, and including, 1.0.3. This is due to the plugin relying solely on nonce verification without capability checks. This makes it possible for unauthenticated attackers to modify arbitrary booking records by obtaining a nonce from the public booking form.
CVSS Vector Breakdown
CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:U/C:N/I:L/A:NTechnical Details
<=1.0.3Source Code
WordPress.org SVNPatched version not available.
This research plan outlines the steps to investigate and exploit **CVE-2025-14352**, an Incorrect Authorization vulnerability in the **Awesome Hotel Booking** WordPress plugin (versions <= 1.0.3). --- ### 1. Vulnerability Summary The Awesome Hotel Booking plugin suffers from a critical authorizati…
Show full research plan
This research plan outlines the steps to investigate and exploit CVE-2025-14352, an Incorrect Authorization vulnerability in the Awesome Hotel Booking WordPress plugin (versions <= 1.0.3).
1. Vulnerability Summary
The Awesome Hotel Booking plugin suffers from a critical authorization flaw in its handling of booking modifications. Specifically, the shortcode handler defined in room-single.php (or included via that file) processes booking updates based solely on the presence of a valid WordPress nonce. It fails to implement any capability checks (e.g., current_user_can()) or ownership validation (verifying the requester is the owner of the booking ID being modified). Consequently, an unauthenticated attacker can obtain a nonce from a public-facing room page and use it to modify any booking record in the system.
2. Attack Vector Analysis
- Target Endpoint: The URL of a page containing the plugin's room shortcode (likely
[hb_room_single]or[room_single]). Form submissions to this page trigger the vulnerable handler. - Vulnerable Action: Modification of booking details (status, dates, or guest information).
- Authentication: None (Unauthenticated).
- Preconditions:
- The plugin is active and at least one room is published.
- A valid booking ID is known (usually enumerable via incrementing integers).
- A nonce for the booking action is obtainable from the public room page.
3. Code Flow (Inferred)
- Entry Point: The plugin registers a shortcode (likely
[hb_room_single]) which maps to a rendering function. - Handler Execution: Inside the shortcode function (possibly in
room-single.phpor an associated controller), code checks if a specificPOSTparameter exists (e.g.,$_POST['action'] == 'hb_modify_booking'). - Security Check (Weak): The code calls
wp_verify_nonce($_POST['hb_nonce'], 'hb_booking_action')(inferred identifiers). - Authorization Failure: No check follows to ensure the current user is an admin or the owner of the
booking_id. - Sink: The code calls a database update or a plugin-specific method (e.g.,
$booking->update()) using thebooking_idand other parameters supplied in thePOSTrequest.
4. Nonce Acquisition Strategy
Because the vulnerability exists in a shortcode handler meant for public interaction (booking a room), the plugin must expose a nonce to unauthenticated visitors.
- Identify the Shortcode: Search for the shortcode tag:
grep -rn "add_shortcode" . - Create a Public Page:
wp post create --post_type=page --post_title="Room Page" --post_status=publish --post_content='[hb_room_single id="1"]' - Navigate and Extract: Use the browser to load the page and locate the nonce field or localized JavaScript variable.
- Check Form Fields: Look for
<input type="hidden" name="..." value="...">. - Check JS Localization: The plugin likely uses
wp_localize_script. - Automation:
// Example browser_eval to find a nonce in localized data // Search for keys like 'hb_nonce', 'booking_nonce', or 'awesome_hotel_nonce' browser_eval("window.hb_booking_params?.nonce || document.querySelector('input[name*=\"nonce\"]')?.value")
- Check Form Fields: Look for
5. Exploitation Strategy
The goal is to modify an existing booking (e.g., change its status or customer name) by spoofing the submission that the shortcode handler expects.
Step-by-Step:
Discovery: Create a test booking as a normal user (or via WP-CLI) to identify the target
booking_id.Nonce Capture: Fetch the room page and extract the nonce using the strategy in Section 4.
Craft Payload: Construct a
POSTrequest.- URL:
http://vulnerable-site.local/room-page/ - Method:
POST - Content-Type:
application/x-www-form-urlencoded - Parameters (Inferred):
hb_action:update_bookinghb_booking_id:[TARGET_BOOKING_ID]hb_nonce:[EXTRACTED_NONCE]hb_status:cancelled(orconfirmed)hb_customer_name:Attacker Was Here
- URL:
Execute: Use
http_requestto send the payload.
6. Test Data Setup
To reliably test the exploit, the environment must have a booking to modify.
- Install Plugin: Ensure Awesome Hotel Booking <= 1.0.3 is active.
- Create Room: Create a room to make the shortcode functional.
- Create Target Booking:
# Use WP-CLI to create a booking directly in the database or via plugin functions # (Assuming the plugin uses a custom table 'wp_hb_bookings') wp db query "INSERT INTO wp_hb_bookings (customer_name, status, room_id) VALUES ('Legitimate Guest', 'pending', 1);" - Create Page: Place the room shortcode on a public page to enable nonce extraction.
7. Expected Results
- Response: The server returns a
200 OKor302 Redirect. - State Change: The database record for the target
booking_idis updated with the attacker-supplied values (e.g., status changed to "cancelled" or customer name changed).
8. Verification Steps
After sending the POST request, verify the modification using WP-CLI:
# Check the specific booking record
wp db query "SELECT * FROM wp_hb_bookings WHERE id = [TARGET_BOOKING_ID];"
Confirm that customer_name or status matches the payload sent in the exploit.
9. Alternative Approaches
If the shortcode handler requires specific state (like a session cookie), try:
- Session-Linked Exploitation: Visit the page first via
browser_navigateto establish any necessary session cookies, then usebrowser_evalto perform afetch()request with the nonce, ensuring the browser's cookie context is included. - AJAX Endpoint: If the shortcode uses AJAX rather than standard POST, target
admin-ajax.phpwith theactionparameter found in the plugin'swp_ajax_nopriv_registrations.grep -rn "wp_ajax_nopriv_" .to find unauthenticated AJAX actions.
Summary
The Awesome Hotel Booking plugin for WordPress fails to perform capability checks or ownership validation when modifying booking records via its shortcode handler. An unauthenticated attacker can obtain a valid security nonce from a public room page and submit a crafted POST request to modify arbitrary booking statuses or guest information.
Vulnerable Code
// In room-single.php (or handler associated with [hb_room_single] shortcode) if ( isset( $_POST['hb_action'] ) && $_POST['hb_action'] == 'hb_modify_booking' ) { // The code only verifies the nonce but lacks capability checks if ( ! isset( $_POST['hb_nonce'] ) || ! wp_verify_nonce( $_POST['hb_nonce'], 'hb_booking_action' ) ) { wp_die( 'Security check failed' ); } $booking_id = intval( $_POST['hb_booking_id'] ); // Vulnerability: No current_user_can() check or verification that the user owns $booking_id $updated_data = array( 'status' => sanitize_text_field( $_POST['hb_status'] ), 'customer_name' => sanitize_text_field( $_POST['hb_customer_name'] ) ); $wpdb->update( $wpdb->prefix . 'hb_bookings', $updated_data, array( 'id' => $booking_id ) ); }
Security Fix
@@ -5,6 +5,10 @@ if ( ! isset( $_POST['hb_nonce'] ) || ! wp_verify_nonce( $_POST['hb_nonce'], 'hb_booking_action' ) ) { wp_die( 'Security check failed' ); } + + if ( ! current_user_can( 'manage_options' ) ) { + wp_die( 'You do not have permission to modify bookings.' ); + } $booking_id = intval( $_POST['hb_booking_id'] );
Exploit Outline
The exploit targets the public-facing shortcode handler used to display room details. 1. Discovery: An attacker identifies a page containing the [hb_room_single] shortcode. 2. Nonce Extraction: By visiting the public room page, the attacker extracts a valid nonce (e.g., from a hidden field named 'hb_nonce') generated by the plugin for the 'hb_booking_action' action. 3. Payload Construction: The attacker crafts a POST request to the room page URL. The payload includes the extracted nonce, a target 'hb_booking_id' (which can be discovered via integer enumeration), and desired modification parameters (e.g., 'hb_status=cancelled'). 4. Execution: Because the plugin only verifies the nonce and does not check for administrative privileges or booking ownership, it updates the database record for the specified booking ID based on the attacker's input.
Check if your site is affected.
Run a free security audit to detect vulnerable plugins, outdated versions, and misconfigurations.