If you’ve spotted a 499 Client Closed Request
error in your server logs pointing to /wp-admin/admin-ajax.php
, your first instinct might be panic—especially if the request originates from your own server IP. But don’t worry: this isn’t always a hack attempt. In most cases, it’s a sign of misconfigured background tasks or resource limits. Let’s break down why this happens and how to fix it.
Breaking Down the Log Entry
The log entry likely looks something like this:
198.51.100.45 - - [07/Mar/2025:17:15:01 -0600] "POST /wp-admin/admin-ajax.php?action=as_async_request_queue_runner&nonce=a1b2c3d4e5 2.0" 499 0 "-" "WordPress/6.7.2; https://peery.me"
Here’s what’s happening:
- IP Address: The request comes from your server’s own IP (internal process).
- Endpoint:
admin-ajax.php
is WordPress’s workhorse for background tasks. - Action Hook:
as_async_request_queue_runner
ties to plugins like Action Scheduler. - 499 Status: The client (your server) terminated the request prematurely.
Why Your Server is Calling Itself
WordPress relies on admin-ajax.php
for internal workflows, such as:
- Plugin Background Tasks: Action Scheduler, WooCommerce, or email plugins use this endpoint to process queues.
- Cron Jobs: WordPress’s pseudo-cron system triggers scheduled tasks (e.g., updates, cleanup).
- Nonce Validation: The
nonce
parameter ensures the request is legitimate and from your site.
The 499
error occurs when the server closes the connection before completing the task. Common culprits include:
- PHP Timeouts: Tasks exceeding
max_execution_time
(default: 30 seconds). - Memory Limits: PHP running out of memory.
- Overlapping Cron Jobs: Multiple tasks competing for resources.
How to Fix the 499 Error
1. Identify the Plugin Causing the Request
- Use WP Crontrol to inspect scheduled tasks tied to
as_async_request_queue_runner
. - Check plugins like Action Scheduler, WooCommerce, or MailPoet for background task settings.
2. Optimize PHP and Server Limits
- Increase PHP Timeout:
Editphp.ini
:max_execution_time = 300 // 5 minutes
- Boost Memory Limits:
memory_limit = 256M
3. Replace WordPress Cron with a Real Cron Job
WordPress’s default cron relies on visitor traffic, which can cause delays. Instead, use a server-level cron:
- Disable the default cron in
wp-config.php
:define('DISABLE_WP_CRON', true);
- Add a cron job via your server’s terminal:
*/5 * * * * wget -q -O - https://yourdomain.com/wp-cron.php?doing_wp_cron >/dev/null 2>&1
4. Fix Server Time Conflicts
If the log shows a future timestamp (e.g., 2025), sync your server’s clock:
timedatectl set-timezone America/Chicago # Replace with your timezone
systemctl restart nginx/php-fpm
5. Monitor and Debug
- Enable WordPress debug logs:
define('WP_DEBUG', true); define('WP_DEBUG_LOG', true);
- Use New Relic or Query Monitor to track long-running tasks.
Preventing Future 499 Errors
- Audit Plugins: Ensure background task plugins are updated and optimized.
- Use a Staging Site: Test resource-heavy tasks before deploying to production.
- Enable Caching: Reduce server load with Redis or Memcached.
Conclusion
A 499
error from admin-ajax.php
is often a “self-inflicted” issue caused by server limits or plugin tasks—not a hack. By optimizing PHP settings, replacing WordPress cron with system cron, and monitoring resource usage, you can eliminate these errors and keep your site running smoothly.
Need more help? Share your log snippet in the comments below!