Laravel Horizon on one VPS: queue discipline for a CMS that sends mail and images

Short answer: aviwebsquad.in runs Horizon on the same VPS as nginx because queue volume is modest—media conversions, mail, and occasional imports—not millions of jobs/hour.

Queues on this stack

Job type Queue Notes
Spatie image conversions default CPU-heavy; timeout > longest conversion
Contact form mail mail isolated so bulk work does not delay
Future: newsletter sends newsletter rate-limited

Supervisor settings (pragmatic)

'production' => [
    'supervisor-1' => [
        'connection' => 'redis',
        'queue' => ['default', 'mail'],
        'balance' => 'auto',
        'maxProcesses' => 3,
        'tries' => 3,
    ],
],

On a 2 vCPU box, maxProcesses: 3 is already aggressive when Vite builds run on deploy.

Horizon auth

Gate viewHorizon restricts dashboard to admin users—never public /horizon.

Monitoring hooks

When I would split workers

Traffic 10× or dedicated newsletter bursts—until then, CI/CD deploy script restarts Horizon after release.

FAQ

Redis on aaPanel?

Installed via panel app store; bind localhost only.

Failed jobs pile up?

horizon:purge after fixing bug; do not silence LongWaitDetected without investigation.

Related: scheduling posts

Published_at scheduling does not use queues—DB time comparison only.

Deploy interaction

deploy_production.sh runs php artisan horizon:terminate gracefully—workers finish current job before exit.

Memory leaks in image jobs

Restart workers nightly via scheduler horizon:terminate at 04:00 if maxJobs not set—cheap insurance on long-running PHP.

Local Sail parity

Horizon container matches Redis 7; queue names identical to prod reduces “works on my machine” for mail jobs.

FAQ (extended)

Database queue driver?

Never on this project—Redis already required for Pulse ingest option.

Horizon metrics in AdSense era?

Unrelated to monetization but prevents silent job death during traffic spikes after approval.