CVE-2026-7648 Overview
CVE-2026-7648 is a payment bypass vulnerability in the LearnPress – WordPress LMS Plugin for Create and Sell Online Courses. The flaw affects all plugin versions up to and including 4.3.5. The REST API endpoint passes unsanitized request parameters to the add_to_cart() function, where array_merge() allows attacker-controlled values to overwrite hardcoded defaults. Authenticated users with subscriber-level access can enroll in any paid course free of charge by supplying a quantity value of zero. This forces the order total to calculate as $0 and bypasses payment gateway validation. The weakness is categorized under [CWE-639] (Authorization Bypass Through User-Controlled Key).
Critical Impact
Authenticated subscribers can bypass payment requirements and enroll in any paid course at no cost, causing direct revenue loss to LearnPress-powered learning platforms.
Affected Products
- LearnPress – WordPress LMS Plugin for Create and Sell Online Courses
- All versions up to and including 4.3.5
- WordPress installations using the vulnerable REST API endpoint in class-lp-rest-courses-controller.php
Discovery Timeline
- 2026-05-14 - CVE CVE-2026-7648 published to NVD
- 2026-05-14 - Last updated in NVD database
Technical Details for CVE-2026-7648
Vulnerability Analysis
The vulnerability stems from improper handling of user-supplied request parameters in the LearnPress REST API endpoint. The frontend courses controller located at inc/rest-api/v1/frontend/class-lp-rest-courses-controller.php accepts an array of parameters from the client and forwards it directly to the cart logic in inc/cart/class-lp-cart.php. Inside add_to_cart(), PHP's array_merge() function combines hardcoded defaults with the attacker-supplied array. Because array_merge() allows later values to overwrite earlier ones, an attacker can override trusted server-side defaults, including the quantity field. The cart subtotal multiplies the course price by quantity, so a supplied quantity of zero produces a total of $0. The checkout flow then treats the order as fully paid and grants course enrollment without invoking any payment gateway.
Root Cause
The root cause is unsafe parameter merging that trusts client input over server-defined defaults. The REST endpoint performs no allowlist filtering on the parameters forwarded to add_to_cart(). Hardcoded cart defaults intended to remain immutable are exposed to client overwrites through array_merge(). This pattern aligns with [CWE-639], where authorization decisions rely on user-controlled keys.
Attack Vector
An attacker requires authenticated access at the subscriber role or higher, which is the default registration level on most LearnPress sites with open enrollment. The attacker sends a crafted POST request to the vulnerable REST API endpoint with a quantity parameter set to zero alongside the target course identifier. The server merges this value into the cart, calculates a zero total, and completes the order without payment. No user interaction is required beyond the attacker's own session. Specific request crafting details are available in the Wordfence Vulnerability Report and the WordPress LearnPress REST API Code.
Detection Methods for CVE-2026-7648
Indicators of Compromise
- Completed LearnPress course orders with a total of $0.00 for courses that have a non-zero list price.
- REST API requests to LearnPress course endpoints containing a quantity parameter equal to 0.
- New course enrollments by subscriber-level accounts immediately after registration, without corresponding payment gateway transactions.
- Discrepancies between LearnPress order counts and the merchant of record's payment processor records.
Detection Strategies
- Review WordPress and LearnPress order logs for orders whose subtotal equals zero but reference paid courses.
- Inspect web server access logs for POST requests to /wp-json/lp/v1/ course endpoints carrying quantity=0.
- Correlate user registration timestamps with subsequent enrollment events to flag suspicious sequences.
- Compare enrollment records against payment gateway settlement reports to identify unmatched enrollments.
Monitoring Recommendations
- Enable verbose logging for the LearnPress REST API and retain logs for at least 90 days.
- Alert on any HTTP request to LearnPress endpoints that contains numeric parameters set to zero or negative values.
- Monitor user role changes and bulk enrollment activity originating from a single IP address.
- Track week-over-week trends in zero-value orders to detect exploitation campaigns.
How to Mitigate CVE-2026-7648
Immediate Actions Required
- Update the LearnPress plugin to a version newer than 4.3.5 as soon as the vendor publishes a fixed release.
- Audit existing LearnPress orders for entries with a $0.00 total tied to paid courses and revoke unauthorized enrollments.
- Restrict new user self-registration on WordPress sites that rely on LearnPress for paid content where feasible.
- Rotate any administrative credentials if unauthorized course access is confirmed.
Patch Information
The vendor fix is tracked in the WordPress LearnPress Changeset. Site administrators should install the patched version of LearnPress through the WordPress plugin updater and verify the version reported in the WordPress admin matches a release later than 4.3.5. Refer to the Wordfence Vulnerability Report for the authoritative fix version.
Workarounds
- Deploy a Web Application Firewall (WAF) rule that blocks requests to LearnPress REST endpoints containing quantity values less than or equal to zero.
- Temporarily disable the LearnPress plugin on sites that cannot apply the patch immediately and serve paid courses through an alternate channel.
- Force manual administrator approval for new course enrollments until the patch is deployed.
- Restrict access to the LearnPress REST API to authenticated sessions that have completed a verified payment workflow.
# Example WAF rule (ModSecurity) to block zero-quantity cart requests
SecRule REQUEST_URI "@contains /wp-json/lp/v1/" \
"chain,phase:2,deny,status:403,id:1026764801,\
msg:'LearnPress CVE-2026-7648 payment bypass attempt'"
SecRule ARGS:quantity "@le 0" "t:none"
Disclaimer: This content was generated using AI. While we strive for accuracy, please verify critical information with official sources.


