How to Troubleshoot High CPU Usage on WordPress: Complete Guide
This guide explains how to troubleshoot high CPU usage on WordPress by checking PHP-FPM, plugins, WP-Cron, database queries, caching, traffic, and external requests.
How to Troubleshoot High CPU Usage on WordPress
What Causes High CPU Usage in WordPress?
WordPress itself is rarely the complete explanation for sustained CPU consumption. A request normally passes through the web server and PHP runtime before WordPress loads its plugins, theme, queries the database, processes application logic, and generates a response. A problem anywhere in that chain can increase CPU demand.
Common causes include:
- Plugins performing expensive PHP operations on every request.
- Poorly optimized themes or custom code.
- Heavy database queries or inefficient application logic.
- Large amounts of autoloaded WordPress options.
- WP-Cron jobs running frequently or taking too long.
- WooCommerce background processing, reports, imports, exports, or synchronization tasks.
- High traffic without an effective page cache.
- Persistent object caching not being available where it would help.
- External API requests that keep PHP workers busy.
- PHP-FPM worker saturation.
- Bot or crawler traffic generating large numbers of uncached requests.
- Malware, compromised plugins, or unexpected automated activity.
- Insufficient server resources for the site’s workload.
WordPress’s official performance documentation identifies page caching, object caching, server caching, and opcode caching as important performance mechanisms. Persistent object caching can reduce repeated database work, while page caching can prevent many requests from reaching PHP at all. WordPress Cache Documentation and WordPress Optimization Documentation provide the relevant technical background.
First: Confirm That WordPress Is Actually Causing the CPU Spike
Do not assume that a CPU alert automatically means a WordPress plugin is responsible. The database server, web server, PHP-FPM, a backup process, malware scanner, image-processing job, or another application on the same server can consume CPU.
Check CPU at the Server Level
On Linux hosting, commands such as top or htop can show which processes are consuming CPU. Look for processes such as PHP-FPM, the web server, MySQL/MariaDB, command-line PHP processes, and unexpected processes.
topIf PHP-FPM workers dominate CPU consumption, WordPress or another PHP application is a strong candidate. If MySQL or MariaDB dominates, investigate database activity rather than immediately disabling plugins.
Look for Patterns Instead of a Single Snapshot
A brief CPU spike during a backup, import, image conversion, deployment, or scheduled task is different from sustained CPU saturation.
Record:
- When CPU usage increases.
- How long the spike lasts.
- Whether it happens at regular intervals.
- Which URLs receive traffic during the spike.
- Whether the database or PHP-FPM becomes saturated at the same time.
- Whether the problem occurs on the frontend, in wp-admin, or both.
This timeline often provides more useful information than a generic statement such as “WordPress is using too much CPU.”
Check PHP-FPM and Worker Saturation
PHP-FPM is a FastCGI process manager designed for PHP applications under load. It provides process management, logging, slow-request diagnostics, and status information that can be useful when investigating PHP workloads. PHP-FPM Documentation describes these capabilities.
If many PHP-FPM workers are busy simultaneously, the problem may be excessive request volume, slow PHP execution, long-running external requests, expensive database operations, or an undersized PHP worker pool.
When available, the PHP-FPM status page can expose information about the current pool. PHP’s documentation recommends restricting access to the status endpoint because it can reveal request and resource information. PHP-FPM Status Documentation
Why Increasing PHP Workers Is Not Always the Solution
Increasing the number of PHP workers can allow more requests to execute concurrently, but it does not make expensive PHP code cheaper. If every request performs heavy database queries or CPU-intensive processing, adding workers can increase contention for CPU and memory.
Think of PHP-FPM workers as workers sharing a finite machine. If the machine is already CPU-bound, adding more workers can create more concurrent work without increasing the CPU capacity available to complete it.
Use WP-CLI to Profile WordPress
For developers and administrators with command-line access, WP-CLI’s wp profile command is one of the most useful ways to identify slow WordPress execution paths.
The official WP-CLI documentation describes the command as a way to identify what is slow in WordPress. It can profile stages such as bootstrap, the main query, and template processing, and it can drill into hooks and arbitrary code execution. WP-CLI Profile Documentation
wp package install wp-cli/profile-command
wp profile stage --fields=stage,time,cache_ratio
wp profile stage bootstrap --fields=hook,time,cache_ratio --spotlightThe exact output will vary by site. The important point is to identify where execution time is being spent instead of guessing which plugin is responsible.
What to Look for in a Profile
- A plugin or theme hook that consistently consumes substantial execution time.
- Unexpectedly expensive bootstrap activity.
- Slow main-query processing.
- Repeated callbacks performing similar work.
- Low cache effectiveness combined with expensive application work.
A profiler identifies execution cost; it does not automatically prove that the corresponding plugin is defective. A plugin may legitimately perform expensive work for a particular feature. The next step is to understand why that work is occurring and whether it is necessary on every request.
Test Plugins Systematically
Plugins are a common source of CPU-intensive workloads because they can execute PHP code during WordPress bootstrap, frontend requests, administrative requests, scheduled events, AJAX calls, REST requests, and background processing.
The safest diagnostic approach is to test on staging first. If the CPU problem disappears when a component is disabled, re-enable components one at a time until the behavior returns.
WP-CLI can deactivate individual plugins or all plugins, with options for excluding selected plugins. WP-CLI Plugin Deactivation Documentation
wp plugin deactivate plugin-slugFor a broader isolation test:
wp plugin deactivate --allDo not run a blanket deactivation on a production WooCommerce store without understanding the consequences. Payment, checkout, security, caching, fulfillment, and other essential functionality can depend on active plugins.
Plugins Deserve Extra Attention When They Perform These Tasks
- Frequent database searches or large queries.
- Real-time statistics and analytics.
- External API synchronization.
- Large product or content imports.
- Image manipulation.
- Search indexing.
- Security scanning.
- Backup generation.
- Broken or repeatedly retried background jobs.
- Large administrative dashboards.
Investigate WP-Cron
WP-Cron is WordPress’s scheduling mechanism for time-based tasks. WordPress checks scheduled events when requests occur, and tasks that are due can run during that process. Core features and plugins can both use WP-Cron. WordPress Cron Documentation
This makes WP-Cron a frequent suspect when CPU usage appears in periodic bursts.
List Scheduled Events
With WP-CLI, you can inspect scheduled events:
wp cron event listThe official command exposes information such as the hook, next run time, recurrence, and related event data. WP-CLI Cron Event List Documentation
Look for unusually frequent events, repeated hooks, large numbers of scheduled jobs, and events that correspond with the exact time of the CPU spike.
Run Due Events Manually During Testing
WP-CLI can execute events that are currently due:
wp cron event run --due-nowIf a particular scheduled operation causes a noticeable CPU increase when executed, you have a much stronger lead than simply knowing that “WordPress uses CPU.” WP-CLI Cron Event Documentation
Should You Disable WP-Cron?
Disabling WP-Cron can be appropriate on some sites when a real system scheduler is configured to execute WordPress’s scheduled tasks. It should not be treated as a universal performance fix.
WordPress documents the DISABLE_WP_CRON configuration constant for disabling the built-in trigger. WordPress wp-config.php Documentation
define( 'DISABLE_WP_CRON', true );If you disable WP-Cron, make sure an alternative scheduler is actually configured. Otherwise scheduled tasks may stop running as expected.
Inspect Database-Related CPU Usage
High CPU can originate from database work rather than PHP computation itself. A request that repeatedly executes expensive queries can keep both PHP workers and the database busy.
Common warning signs include:
- Slow wp-admin pages.
- Slow WooCommerce product or order screens.
- Search requests that consume significant resources.
- Large or inefficient queries.
- Repeated queries triggered by plugins.
- Large option values loaded on many requests.
- Database activity increasing together with PHP-FPM CPU.
Use WP-CLI to Inspect Database Information
WP-CLI provides database commands for checking, optimizing, querying, and inspecting WordPress databases. WP-CLI Database Documentation
wp db check
wp db size
wp db tablesFor more advanced diagnostics, wp db query can execute SQL using the credentials configured in wp-config.php. WP-CLI db query Documentation
Do not run destructive SQL statements against production simply because a database query appears in a troubleshooting guide. Export or back up the relevant data first and understand the query before modifying anything.
Check Autoloaded WordPress Options
WordPress loads certain options automatically during startup. If plugins or themes leave excessive amounts of data configured for autoloading, every request can carry unnecessary initialization overhead.
WordPress’s performance documentation specifically discusses autoloaded options and recommends keeping autoloaded data under control. It also notes that persistent object caching can make option retrieval more efficient. WordPress Optimization Documentation
WP-CLI can show the total size of autoloaded options:
wp option list --autoload=on --format=total_bytesIt can also list the individual options and their sizes:
wp option list --autoload=on --fields=option_name,size_bytes --format=tableThe correct response is not to disable autoloading randomly. First determine which plugin or theme owns the option and whether the option actually needs to be loaded during normal WordPress initialization.
Current WordPress APIs also provide explicit mechanisms for controlling an option’s autoload behavior. For example, wp_set_option_autoload() exists for setting the autoload state programmatically. wp_set_option_autoload() Documentation
Check Persistent Object Caching
WordPress has an object-cache API, but the default object cache is not persistent across requests. A persistent object cache can retain cached objects between requests and reduce repeated database work. WordPress Object Cache Documentation
Persistent object caching is particularly relevant when the site repeatedly reads the same data from the database and the hosting environment supports an appropriate cache backend.
However, object caching is not a substitute for fixing an inefficient query. If an application continuously generates unique or poorly designed queries, adding a cache may only hide part of the underlying problem.
Use Page Caching to Reduce PHP Work
Page caching can prevent WordPress from rebuilding the same public response for every request. Instead, a cached representation can be served without executing the complete WordPress/PHP stack for every visitor.
WordPress’s official performance documentation describes caching as one of the fastest ways to improve performance and distinguishes page caching, browser caching, object caching, and server caching. WordPress Cache Documentation
For a mostly static content site, effective page caching can dramatically reduce the amount of PHP work required to serve public pages. Dynamic sites require more careful cache rules because personalized or frequently changing responses cannot always be served from the same cache.
What Page Caching Does Not Fix
- Expensive uncached wp-admin requests.
- WooCommerce operations that must execute dynamically.
- WP-Cron jobs.
- CLI scripts.
- Background imports and exports.
- Slow external API calls.
- Malicious or abnormal requests that bypass the cache.
- CPU-intensive plugin logic that runs before or outside the cached response path.
Check PHP OPcache
PHP OPcache stores precompiled PHP bytecode in shared memory, avoiding the need to load and parse PHP scripts for every request. The PHP manual documents OPcache as a PHP performance feature. PHP OPcache Documentation
WordPress also recommends opcode caching as part of server-side performance optimization. WordPress Cache Documentation
If OPcache is unavailable, incorrectly configured, or too constrained for the application, PHP may perform unnecessary compilation work. That does not mean OPcache is the root cause of every high-CPU incident, but it is worth checking when you control the PHP environment.
Do not blindly copy arbitrary php.ini settings from performance articles. PHP’s configuration options and appropriate values depend on the PHP version, workload, memory availability, deployment model, and application. PHP OPcache Configuration Documentation
Investigate External HTTP Requests
Plugins frequently communicate with third-party services for payment processing, analytics, licensing, email, shipping, product synchronization, APIs, and other functions.
A slow external request can keep a PHP worker occupied for longer than expected. If many requests wait on the same remote service, PHP-FPM workers can accumulate and CPU usage may rise as the application continues processing other work around those requests.
Look for:
- Requests to remote APIs during every page load.
- Repeated API retries.
- Missing or excessive timeouts.
- Synchronization jobs running too frequently.
- Third-party services that have recently become slow or unavailable.
Where possible, external synchronization should be decoupled from the critical frontend request path and processed asynchronously. The exact implementation depends on the plugin or application architecture.
Check Traffic, Bots, and Uncached Requests
High CPU does not always mean a single request is inefficient. A perfectly reasonable WordPress request can become a server problem when thousands of requests arrive concurrently.
Review access logs and analytics for:
- Sudden traffic increases.
- Large numbers of requests from a small set of IP addresses.
- Repeated requests to expensive URLs.
- Search endpoints being abused.
- Login attempts.
- XML-RPC or REST API activity where relevant to the site.
- Requests bypassing the page cache.
- Unknown crawlers generating unusually high request rates.
If traffic is legitimate, scaling and caching may be appropriate. If the traffic is abusive, rate limiting, web-server controls, CDN protection, or other security measures may be more appropriate than simply allocating more CPU.
Turn on WordPress Debug Logging Carefully
When errors or warnings are contributing to repeated failures, debug logging can reveal useful information. WordPress documents WP_DEBUG_LOG for recording debug information in a log file, while WP_DEBUG_DISPLAY can prevent those messages from being displayed directly in page output. WordPress Debugging Documentation
A typical troubleshooting configuration is:
define( 'WP_DEBUG', true );
define( 'WP_DEBUG_LOG', true );
define( 'WP_DEBUG_DISPLAY', false );Use debugging deliberately and remove or disable it when it is no longer needed, especially on production sites. Logs can contain sensitive operational information depending on the application.
Use PHP-FPM Slow Logs for Difficult Cases
If you control PHP-FPM configuration, its slow-log capability can provide deeper evidence about unusually slow PHP execution. PHP-FPM documentation describes slow logging as a mechanism that can record scripts and PHP backtraces for unusually slow executions. PHP-FPM Documentation
This is particularly useful when normal WordPress profiling does not explain why workers remain busy.
Because PHP-FPM configuration varies by hosting environment, do not copy pool configuration blindly. Managed hosting providers may control these settings, in which case the appropriate request is to provide the provider with the time window, affected domain, URLs, and observed CPU/PHP-FPM behavior.
WooCommerce-Specific CPU Problems
WooCommerce stores can have more demanding workloads than simple content sites because orders, products, customers, payments, inventory, reports, integrations, scheduled tasks, and administrative operations can all generate application and database work.
When troubleshooting a WooCommerce site, correlate CPU usage with:
- Order imports or exports.
- Product synchronization.
- Inventory updates.
- Analytics or reporting jobs.
- Payment or shipping integrations.
- Email processing.
- Large catalog searches.
- Scheduled background tasks.
- Bulk product or order operations.
A WooCommerce store should not be diagnosed solely from frontend page speed. A store may have acceptable cached storefront performance while consuming substantial resources in administration and background processing.
Common Troubleshooting Mistakes
Installing More Caching Plugins
Adding multiple overlapping optimization plugins can make troubleshooting harder and may create conflicting cache rules or duplicate processing. Establish what caching already exists at the application, web-server, CDN, and object-cache layers before adding another solution.
Increasing CPU Before Finding the Workload
More CPU can be a valid scaling decision, particularly when traffic has legitimately grown. But if a plugin is executing an expensive operation unnecessarily, additional CPU may only postpone the problem.
Disabling Plugins at Random
Randomly disabling plugins without recording the result makes diagnosis difficult. Change one variable at a time where possible and record the CPU behavior before and after the change.
Deleting Database Data Without Understanding Ownership
Large options, transients, logs, metadata, and custom tables can be tempting cleanup targets. Do not delete data simply because it looks large. Determine which component created it, whether it is still required, and whether the plugin provides a supported cleanup mechanism.
Changing PHP-FPM Settings Without Monitoring Memory
More PHP workers can increase concurrent processing, but each worker consumes resources. A configuration that appears to solve CPU queuing can create memory pressure and swapping if the server is undersized.
A Practical Diagnostic Workflow
If you need a repeatable process, use this sequence rather than changing several settings at once.
- Confirm the CPU spike. Establish whether it is sustained, periodic, or traffic-related.
- Identify the dominant process. Determine whether PHP-FPM, the database, web server, or another process is consuming CPU.
- Correlate the timing. Compare CPU spikes with traffic, cron events, backups, imports, and scheduled tasks.
- Profile WordPress. Use WP-CLI profiling or another appropriate application profiler.
- Test plugins and themes. Use staging whenever possible and isolate components systematically.
- Inspect WP-Cron. Look for frequent, duplicated, or expensive scheduled tasks.
- Investigate database activity. Look for expensive queries and excessive autoloaded data.
- Review caching. Confirm that page caching and persistent object caching are appropriate for the site.
- Check external requests. Identify remote services that may keep PHP workers busy.
- Review traffic and security logs. Determine whether bots, attacks, or unexpected clients are creating excessive work.
- Optimize or replace the root cause. Fix the expensive component instead of masking it.
- Scale resources if necessary. If the workload is legitimate and optimized, increase CPU, PHP capacity, database capacity, or server resources as appropriate.
Quick Diagnosis Table
| Symptom | Likely Area | What to Check |
|---|---|---|
| CPU spikes at regular intervals | WP-Cron or scheduled jobs | Scheduled events, background processing, imports, backups |
| PHP-FPM dominates CPU | PHP/WordPress execution | Plugins, themes, custom code, profiling, external requests |
| Database dominates CPU | Database workload | Queries, indexes, autoloaded options, application behavior |
| CPU increases with traffic | Request volume | Page cache, CDN, bots, uncached URLs, server capacity |
| wp-admin is particularly slow | Dynamic application workload | Plugins, database queries, reports, WooCommerce operations |
| CPU remains high after traffic falls | Background or stuck workload | Cron, CLI jobs, queues, imports, PHP-FPM processes |
| High CPU begins after a plugin update | Plugin behavior or compatibility | Recent changes, logs, staging rollback test, plugin profile |
When Should You Upgrade Hosting?
Upgrade the server when measurements show that the workload is legitimate and the application is already reasonably optimized.
For example, a busy WooCommerce store may simply require more CPU and memory as traffic, catalog size, order volume, and background processing grow. Scaling is not a failure; it is often the correct engineering decision.
However, upgrading should come after basic diagnosis when possible. A larger server cannot compensate indefinitely for a plugin that performs an expensive query on every request, a cron task that runs continuously, or abusive traffic that bypasses caching.
How to Prevent Future CPU Problems
- Monitor CPU, memory, PHP-FPM, database load, and request volume.
- Keep WordPress, PHP, themes, and plugins maintained and compatible.
- Use page caching where the site’s content model allows it.
- Use persistent object caching when it provides a measurable benefit.
- Review WP-Cron and background jobs periodically.
- Monitor database growth and expensive application queries.
- Keep autoloaded options under control.
- Use staging for major plugin, theme, and configuration changes.
- Monitor external API integrations and synchronization jobs.
- Keep backups and security monitoring in place.
- Document CPU incidents so recurring patterns become easier to identify.
Frequently Asked Questions
Why is WordPress using 100% CPU?
100% CPU usually means the server has more runnable processing work than its available CPU capacity can handle at that moment. The source may be PHP-FPM, database activity, traffic, cron jobs, plugins, custom code, or another server process. Identify the dominant process before changing WordPress settings.
Can a WordPress plugin cause high CPU usage?
Yes. A plugin can consume substantial CPU through expensive PHP operations, database queries, scheduled tasks, external requests, imports, indexing, or background processing. Profiling and controlled plugin isolation are more reliable than guessing from the plugin’s name.
Does caching reduce WordPress CPU usage?
Page caching can reduce the number of requests that need to execute the complete WordPress/PHP stack. Object caching can reduce repeated database work. Neither automatically fixes expensive uncached requests, cron jobs, background processing, or inefficient application code.
Can WP-Cron cause high CPU?
Yes. Plugins and WordPress core can schedule tasks through WP-Cron. Frequent, duplicated, or expensive scheduled events can create periodic workload spikes. Inspect the scheduled event list and correlate event execution with CPU usage.
Should I disable WP-Cron to reduce CPU?
Not automatically. If WP-Cron is responsible for excessive workload, identify the expensive event first. Disabling the built-in WP-Cron trigger can be appropriate when a properly configured alternative scheduler will execute WordPress’s scheduled tasks.
Does increasing PHP-FPM workers fix high CPU?
Not necessarily. More workers can increase concurrency, but if the server is already CPU-bound, additional workers may increase contention. Worker configuration should be based on CPU, memory, request duration, and observed PHP-FPM behavior.
Is high CPU always caused by WordPress?
No. A server may be running database processes, backups, malware scanners, cron jobs, other applications, or unexpected processes. Always identify the process consuming CPU before concluding that WordPress is responsible.
Conclusion
Troubleshooting high CPU usage on WordPress is fundamentally an observability problem. The goal is to identify what work is consuming CPU, when it occurs, and why that work is being performed. Start at the server level, identify PHP-FPM or database pressure, profile WordPress, inspect plugins and scheduled tasks, investigate database and caching behavior, and review traffic and external requests. Once the root workload is known, you can choose the appropriate fix: optimize code, change a plugin configuration, repair a cron task, improve caching, reduce abusive traffic, or scale the server.
The most important principle is simple: measure first, isolate second, optimize third, and scale when the workload genuinely requires it.