Sunday, May 10, 2026

Laravel Queue Workers Stuck on Redis: 5 Stress‑Testing Fixes That Saved My VPS from 12‑Hour Crashes

Laravel Queue Workers Stuck on Redis: 5 Stress‑Testing Fixes That Saved My VPS from 12‑Hour Crashes

If you’ve ever watched your Laravel queue workers grind to a halt while Redis spikes like a heart‑monitor during a code sprint, you know the panic that follows. I’ve spent dozens of nights chasing ghost processes, watching CPU hit 100 % and a VPS trembling under the load. The good news? After a systematic stress‑test and five concrete fixes, my 12‑hour crashes vanished. Below is the exact roadmap that turned my flaky environment into a rock‑solid production engine.

Why This Matters

Queue workers are the backbone of any Laravel‑driven SaaS, handling emails, notifications, image processing, and API throttling. When they stall on Redis, latency spikes, users see timeouts, and revenue drains. In a VPS‑based Laravel‑WordPress hybrid stack, each second of downtime can cost a small business $10–$30 per minute in lost conversions.

Common Causes of Stuck Workers

  • Improper supervisor configuration causing workers to respawn too quickly.
  • Redis maxmemory policies that trigger evictions under load.
  • PHP‑FPM child processes hitting pm.max_children limits.
  • Out‑of‑date Composer autoload files leading to class‑loading deadlocks.
  • Network latency between Nginx and Redis inside Docker or on a shared VPC.

Step‑By‑Step Fix Tutorial

1. Tune Supervisor for Graceful Restarts

Supervisor ensures your queue workers stay alive. A mis‑configured restart or stopwaitsecs can lock processes in a zombie state.

[program:laravel-queue]
process_name=%(program_name)s_%(process_num)02d
command=php /var/www/html/artisan queue:work redis --sleep=3 --tries=3 --timeout=90
autostart=true
autorestart=true
user=www-data
numprocs=8
redirect_stderr=true
stdout_logfile=/var/log/laravel/queue.log
stopwaitsecs=360

2. Adjust Redis maxmemory‑policy

Switching from noeviction to allkeys-lru prevents the server from rejecting writes when memory is full.

# /etc/redis/redis.conf
maxmemory 2gb
maxmemory-policy allkeys-lru

After editing, restart Redis:

sudo systemctl restart redis.service

3. Optimize PHP‑FPM Pools

Too few children throttle concurrent requests; too many exhaust RAM. Find the sweet spot for your VPS.

# /etc/php/8.2/fpm/pool.d/www.conf
pm = dynamic
pm.max_children = 50
pm.start_servers = 10
pm.min_spare_servers = 5
pm.max_spare_servers = 20
request_terminate_timeout = 120

4. Refresh Composer Autoloader in Production Deploys

# Deploy script snippet
composer install --no-dev --optimize-autoloader --prefer-dist
php artisan config:cache
php artisan route:cache
php artisan view:cache

5. Harden Nginx ↔ Redis Connection

Enable TCP keepalive and a short proxy timeout to avoid stale sockets.

# /etc/nginx/conf.d/redis-proxy.conf
upstream redis_backend {
    server 127.0.0.1:6379 keepalive=32;
}
server {
    listen 80;
    server_name api.myapp.com;

    location / {
        proxy_pass http://127.0.0.1:8000;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
    }

    location /redis {
        proxy_pass http://redis_backend;
        proxy_connect_timeout 1s;
        proxy_send_timeout 2s;
        proxy_read_timeout 2s;
        keepalive_timeout 65;
    }
}

VPS or Shared Hosting Optimization Tips

  • Use UFW to lock down Redis to localhost only.
  • Enable swap on small VPS to avoid OOM kills during traffic spikes.
  • Prefer Ubuntu 22.04 LTS for the latest kernel and security patches.
  • If on shared hosting, move the queue to a separate Laravel microservice on a low‑cost DigitalOcean droplet.
  • Activate Cloudflare caching for static assets; it reduces PHP request volume dramatically.

Real World Production Example

My client runs a multi‑tenant SaaS built on Laravel 10 + WordPress for marketing pages. The queue handles 3 k jobs/min during a product launch. Before the fixes, Redis memory hit 2 GB, workers froze, and the VPS rebooted after 12 hours of continuous load.

After applying the five steps, the same launch processed 5 k jobs/min with zero crashes. CPU usage stayed under 45 %, and Redis memory stabilized at 1.1 GB.

Before vs After Results

MetricBeforeAfter
Avg. Queue Latency12 s1.8 s
CPU (peak)98 %42 %
Redis Memory2.4 GB (OOM)1.1 GB
Failed Jobs3 % (1 200)0.2 % (78)

Security Considerations

  • Bind Redis to 127.0.0.1 or use a private VPC subnet.
  • Set a strong requirepass in redis.conf and rotate it quarterly.
  • Enable disable_commands for dangerous Redis commands (FLUSHALL, CONFIG).
  • Run php artisan queue:restart after any code push to purge stale serialized jobs.
  • Use AppArmor or SELinux profiles for PHP‑FPM and Redis processes.

Bonus Performance Tips

These are quick wins you can drop into any Laravel stack.

  1. Leverage Laravel Horizon for real‑time queue monitoring and auto‑scaling.
  2. Set database.php sticky option for read/write splitting if you use a MySQL replica.
  3. Compress JSON API responses with gzip in Nginx.
  4. Use php artisan schedule:work instead of cron for sub‑minute tasks.
  5. Enable HTTP/2 on Nginx to reduce handshake latency for API calls.

FAQ

Q: My VPS is on a shared host; can I still use Supervisor?

A: Most shared providers block background daemons. Switch to a low‑cost VPS (e.g., Hostinger) or use Laravel Forge to manage a dedicated worker dyno.

Q: Should I use Redis clustering?

A: For most <10 k QPS workloads a single 2‑GB instance with allkeys-lru suffices. Cluster only after you consistently hit >30 k QPS.

Final Thoughts

Stuck queue workers are rarely a “code bug” – they are a symptom of resource mis‑alignment. By stress‑testing, tightening Supervisor, Redis, PHP‑FPM, and Nginx, you turn a flaky VPS into a predictable, scalable engine. The five fixes above are reproducible across any Laravel‑WordPress hybrid stack and will save you countless hours of midnight firefighting.

Ready to level up your hosting without breaking the bank? Check out cheap secure hosting from Hostinger – perfect for Laravel queues, Redis, and WordPress sites on a tight budget.

No comments:

Post a Comment