CVE-2026-103365 Overview
The Bookly – Online Scheduling and Appointment Booking System plugin for WordPress contains a sensitive information exposure vulnerability affecting versions up to and including 28.4. The flaw resides in the classic booking form's Details step, where the bookly_render_details AJAX endpoint can be invoked by unauthenticated users. Attackers who know only a registered customer's primary phone number or email address can retrieve that customer's stored name, email, phone, and internal notes. The weakness is tracked as CWE-200: Exposure of Sensitive Information to an Unauthorized Actor.
Critical Impact
Unauthenticated attackers can harvest personally identifiable information (PII) of booking customers using only a known phone number or email address as a lookup key.
Affected Products
- Bookly – Online Scheduling and Appointment Booking System plugin for WordPress
- All versions up to and including 28.4
- Sites using {client_name}, {client_email}, {client_phone}, or {client_note} placeholders in the Details step Appearance information text
Discovery Timeline
- 2026-10-10 - CVE-2026-103365 published to NVD
- 2026-10-13 - Last updated in NVD database
Technical Details for CVE-2026-103365
Vulnerability Analysis
The vulnerability stems from three compounding design errors in the Bookly plugin's booking flow. The bookly_render_details endpoint is registered for both wp_ajax and wp_ajax_nopriv hooks, making it reachable by unauthenticated requests. The booking module overrides the csrfTokenValid() method to always return true, disabling CSRF token validation on the endpoint. The Bookly\Frontend\Components\Booking\InfoText::getCodes() method calls UserBookingData::getCustomer() to load a persisted Customer entity keyed solely on the attacker-supplied phone or email, without invoking the plugin's own customerIdentityConfirmed() predicate.
When a site operator uses the supported {client_name}, {client_email}, {client_phone}, or {client_note} placeholders in the Details step Appearance information text, the matched customer's stored name, email, phone, and internal notes are substituted directly into the returned HTML response.
Root Cause
The root cause is missing identity verification combined with a disabled CSRF check on an unauthenticated endpoint. The customer lookup trusts a single user-controlled identifier (phone or email) as sufficient proof of identity. No ownership-of-identifier challenge, booking token, or session binding is enforced before rendering personal data into the response.
Attack Vector
An unauthenticated remote attacker crafts an HTTP POST request to the WordPress admin-ajax.php endpoint with action=bookly_render_details and a target customer's phone number or email in the booking data payload. If the targeted site has configured any of the {client_*} placeholders in the Details step Appearance text, the plugin returns HTML containing the matched customer's stored fields. The attack requires only network access to the site and knowledge of one registered contact identifier.
No verified public exploit code is published. See the Wordfence Vulnerability Report and the vulnerable InfoText component source for technical details.
Detection Methods for CVE-2026-103365
Indicators of Compromise
- Unauthenticated POST requests to /wp-admin/admin-ajax.php with the parameter action=bookly_render_details
- Repeated requests from a single source iterating through phone numbers or email addresses in the payload
- Unusual spikes in response sizes from the bookly_render_details endpoint, indicating customer data substitution
- Requests to the endpoint from source IPs with no prior booking session cookies or referer context
Detection Strategies
- Deploy web application firewall (WAF) rules to log and alert on unauthenticated calls to the bookly_render_details AJAX action
- Correlate access logs for enumeration patterns against the booking endpoint, such as high request volume with varying phone or email parameters
- Review WordPress audit logs for the installed Bookly plugin version to confirm exposure to versions ≤ 28.4
Monitoring Recommendations
- Monitor outbound response bodies from admin-ajax.php for the presence of customer PII fields when the request originates from unauthenticated sessions
- Alert on sudden increases in bookly_render_details response payload sizes compared to baseline
- Track and rate-limit unauthenticated requests to the Bookly AJAX endpoints at the reverse proxy or CDN layer
How to Mitigate CVE-2026-103365
Immediate Actions Required
- Update the Bookly plugin to version 28.5 or later, which contains the vendor fix documented in the plugin change log
- Remove {client_name}, {client_email}, {client_phone}, and {client_note} placeholders from the Details step Appearance information text until the patch is applied
- Audit WordPress sites in your estate for installed versions of the Bookly plugin at or below 28.4
Patch Information
The vendor released version 28.5 of the Bookly plugin addressing the issue. Site administrators should upgrade through the WordPress plugin management interface or via WP-CLI. Confirm the installed version equals or exceeds 28.5 after upgrade.
Workarounds
- Strip all {client_*} placeholders from the Details step Appearance text, which prevents customer data substitution into the response
- Restrict access to /wp-admin/admin-ajax.php?action=bookly_render_details at the WAF for unauthenticated users until patching is complete
- Apply strict rate limiting on the booking AJAX endpoint to slow enumeration attempts against known customer identifiers
# Example WP-CLI upgrade command
wp plugin update bookly-responsive-appointment-booking-tool --version=28.5
wp plugin get bookly-responsive-appointment-booking-tool --field=version
Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.

