WooCommerce Checkout Stuck Loading: Causes and How to Fix It
Quick Summary: Resolving the WooCommerce Checkout Spinner
When the WooCommerce checkout page displays an endless loading spinner, it indicates that the asynchronous JavaScript (AJAX) call used to refresh order review data—such as totals, shipping methods, or payment options—failed to complete or returned an invalid response. Always create a full site backup and perform troubleshooting on a staging environment before modifying core configuration files.
- Check Browser Developer Tools: Inspect the browser Console for JavaScript runtime errors and examine the Network tab (filtered by XHR/Fetch) for status codes or malformed server responses.
- Match Site URLs: Verify that WordPress Address (URL) and Site Address (URL) match exactly in settings to prevent cross-origin request failures.
- Clear and Configure Caching: Exclude dynamic checkout endpoints from caching plugins and CDN layers to avoid serving stale security nonces.
- Resolve Theme and Plugin Conflicts: Switch temporarily to a default theme (such as Storefront) and isolate third-party extensions to identify scripts interrupting AJAX execution.
- Verify Memory and Server Limits: Ensure that the WordPress memory limit meets WooCommerce requirements and enable error logging to capture backend PHP exceptions.
| Observed Symptom / Status | Root Cause | Corrective Action |
|---|---|---|
AJAX response returns -1 | WordPress security nonce validation failed due to cached data | Clear plugin/server cache and exclude the checkout page from static caching layers. |
| AJAX returns HTML instead of JSON | PHP notices/errors, caching headers, or an index.html file in root | Remove conflicting root files, disable front-end error display, and audit caching rules. |
| HTTP 403 or 406 Error | Web Application Firewall or hosting rule blocking POST requests | Adjust firewall rules to permit ?wc-ajax=update_order_review requests. |
| HTTP 500 Internal Server Error | PHP memory depletion or unhandled fatal script execution | Check server error logs and verify that WP_MEMORY_LIMIT meets requirements. |
Console shows Uncaught TypeError | Conflicting script in a theme override or third-party plugin | Run a plugin/theme conflict test using Troubleshooting Mode or a staging site. |
How the WooCommerce Checkout Loading Cycle Works
During a checkout session, WooCommerce recalculates totals, taxes, and available payment methods dynamically when customer inputs change (such as selecting a shipping method or modifying a billing address). Instead of reloading the full page, WooCommerce dispatches an AJAX request to its internal endpoint (such as ?wc-ajax=update_order_review) and displays a loading spinner over the order review container.
Under normal conditions, the server validates the security nonce, computes the order details, and returns a structured JSON payload. The client-side JavaScript then updates the checkout layout and removes the loading spinner. If this process is blocked by a network failure, a script error, or invalid payload output, the spinner remains active indefinitely.
Step-by-Step Diagnostic Guide
1. Inspect Browser Console and Network Requests
The fastest way to identify the source of the stall is using your browser's Developer Tools:
- Open the store checkout page in your browser.
- Press
F12(or right-click and choose Inspect) and select the Console tab. Look for red JavaScript error traces that point to a specific script file. - Navigate to the Network tab and filter requests by Fetch/XHR.
- Change an address field or select a different shipping option to trigger the update request.
- Click on the
?wc-ajax=update_order_reviewentry and inspect the Response tab:- Response is
-1: Indicates a security validation failure caused by a cached or expired nonce. - Response is HTML instead of JSON: Indicates that server-side output (such as an unhandled PHP notice or a rogue
index.htmlin the WordPress root directory) is corrupting the JSON payload. - Status 403 / 406: Signals that a hosting security rule or web application firewall intercepted the request.
- Status 500: Signals an unhandled PHP fatal error or exhausted server resources.
- Response is
2. Match WordPress Address and Site Address URLs
Cross-origin security policies prevent browsers from completing AJAX requests when the request origin and destination protocols or domains do not match exactly.
- Log in to your WordPress dashboard.
- Navigate to Settings > General.
- Confirm that WordPress Address (URL) and Site Address (URL) use identical protocols (
http://vshttps://) and domain structures (such as matchingwwwprefixes). - Save changes if updates were made.
If your URLs are defined in wp-config.php, ensure both constants match identically:
define( 'WP_HOME', 'https://example.com' );
define( 'WP_SITEURL', 'https://example.com' );3. Configure Dynamic Caching and CDN Rules
Static caching plugins and edge proxy networks can cache WordPress security nonces. When a customer receives a cached nonce, WooCommerce rejects the background request and returns -1.
- Ensure dynamic checkout pages (
/checkout/,/cart/, and/my-account/) are excluded from page caching and minification tools. - Configure caching engines to bypass requests containing
?wc-ajax=*query strings. - Exclude core WooCommerce scripts from aggressive JavaScript concatenation or deferral settings that alter script execution order.
If your store connects through a reverse proxy and experiences connection dropouts, consult our troubleshooting guide on Cloudflare Error 522 (Connection Timed Out).
4. Test for Theme and Extension Conflicts
Incompatible custom code, outdated template overrides, or JavaScript errors in other plugins can block checkout handlers.
- Use the Health Check & Troubleshooting plugin from WordPress.org to enable Troubleshooting Mode. This isolates changes to your current session without disrupting visitors.
- Switch to a default WordPress theme, such as Storefront.
- Keep only WooCommerce active and test the checkout page.
- If the spinner resolves, reactivate your extensions one by one to find the specific script causing the conflict.
5. Verify Memory Limits and Enable Server Logging
AJAX recalculations require adequate server memory. According to official WooCommerce documentation, the minimum recommended WordPress memory limit is 64 MB (many stores benefit from 128 MB or 256 MB depending on extension requirements).
Check your current allocation under WooCommerce > Status > System Status at the WP Memory Limit row. You can increase this by adding the following line to wp-config.php before the /* That's all, stop editing! */ line:
define( 'WP_MEMORY_LIMIT', '128M' );To log server-side script failures without printing errors directly to the browser (which corrupts JSON output), configure debugging in wp-config.php:
define( 'WP_DEBUG', true );
define( 'WP_DEBUG_LOG', true );
define( 'WP_DEBUG_DISPLAY', false );
@ini_set( 'display_errors', 0 );This writes diagnostic traces directly to /wp-content/debug.log. For database connection failures during high load, refer to our guide on WordPress Error Establishing a Database Connection.
Verification Checklist
After applying fixes, verify checkout stability across key user workflows:
- Test the checkout page in a private or incognito window as a non-logged-in guest customer.
- Change the billing and shipping address fields to confirm that shipping methods and tax totals update seamlessly.
- Apply and remove a coupon code to verify AJAX recalculation.
- Select each enabled payment gateway to ensure its specific form fields and scripts initialize without console errors.
Frequently Asked Questions
Why does the checkout stall when selecting a specific payment gateway?
Payment gateways often load external JavaScript libraries or embedded iframes. If a gateway encounters an invalid API key, strict Content Security Policy (CSP) blocking, or script errors, it can fail to complete its initialization cycle, causing the WooCommerce loading overlay to remain stuck.
Does the WooCommerce Checkout Block fix this issue?
The Checkout Block uses modern REST API endpoints instead of legacy ?wc-ajax=update_order_review requests. While this resolves issues related to legacy jQuery theme overrides, underlying problems—such as server resource limits, REST API endpoint blocking, or mismatched URLs—will still cause checkout disruptions until fixed.