Logo

~/saidqb cat wiki/stack/server-extra/laravel.md

MDlaravel

commit by saidqb

Laravel: setup tambahan (Queue, Reverb, Scheduler)

Lanjutan dari deploy-laravel.md — tiga hal yang paling sering dibutuhkan begitu deploy dasar sudah jalan: queue worker (proses background), Reverb (websocket/realtime), dan task scheduler (cron Laravel). Path & user (laravelapp, /home/laravelapp/app) ikut konvensi dokumen deploy utama.

1. Queue Worker (Supervisor)

php artisan queue:work itu proses long-running — kalau cuma dijalankan manual di terminal, mati begitu SSH terputus. Butuh process manager yang auto-restart kalau crash: Supervisor.

bash
sudo apt install supervisor -y

Rocky Linux/AlmaLinux (Remi): paket Supervisor-nya dari EPEL (sudo dnf install epel-release -y dulu kalau belum ada):

bash
sudo dnf install supervisor -y
sudo systemctl enable --now supervisord

/etc/supervisor/conf.d/laravelapp-worker.conf

ini
[program:laravelapp-worker]
process_name=%(program_name)s_%(process_num)02d
command=php /home/laravelapp/app/artisan queue:work --sleep=3 --tries=3 --max-time=3600
directory=/home/laravelapp/app
autostart=true
autorestart=true
user=laravelapp
numprocs=2
redirect_stderr=true
stdout_logfile=/home/laravelapp/app/storage/logs/worker.log
stopwaitsecs=3600

numprocs=2 — jalankan 2 worker paralel, sesuaikan sama beban queue. stopwaitsecs=3600 kasih waktu worker nyelesain job yang sedang jalan sebelum dipaksa berhenti (dibatasi biar tidak infinite kalau job-nya macet).

Rocky Linux/AlmaLinux (Remi): paket supervisor dari EPEL biasanya default baca folder /etc/supervisord.d/ dengan ekstensi file .ini (bukan /etc/supervisor/conf.d/*.conf seperti Debian/Ubuntu) — cek [include] di /etc/supervisord.conf kalau mau pastikan path yang aktif. Isi filenya sama persis, cuma lokasi & ekstensinya beda:

/etc/supervisord.d/laravelapp-worker.ini

bash
sudo supervisorctl reread
sudo supervisorctl update
sudo supervisorctl start laravelapp-worker:*

Kenapa php artisan queue:restart (di langkah "tiap kali deploy update" dokumen utama) butuh Supervisor: queue:restart sendiri cuma nyalain sinyal — worker yang sedang jalan bakal nyelesain job yang lagi diproses lalu keluar, tidak otomatis nyala lagi. Supervisor-lah (autorestart=true) yang langsung start ulang proses barunya, otomatis kebaca kode terbaru. Tanpa Supervisor (atau sejenisnya), queue:restart cuma mematikan worker selamanya.

Command yang berguna:

bash
sudo supervisorctl status                      # cek worker jalan/tidak
sudo supervisorctl restart laravelapp-worker:*  # restart manual kalau perlu
tail -f /home/laravelapp/app/storage/logs/worker.log

2. Laravel Reverb (WebSocket server)

bash
sudo -iu laravelapp
cd app
composer require laravel/reverb
php artisan reverb:install
exit

reverb:install otomatis nambah konfigurasi ke .env — set BROADCAST_CONNECTION=reverb, isi REVERB_APP_ID/REVERB_APP_KEY/REVERB_APP_SECRET yang di-generate.

Kalau server RHEL-based (CentOS/AlmaLinux/Rocky) pakai PHP dari repo Remi (bukan Ubuntu/Debian seperti contoh apt di dokumen ini): Reverb butuh extension pcntl dan posix, yang di paket php-remi default tidak ikut ter-install bareng php — harus ditambah manual:

bash
sudo dnf install php-pcntl php-posix -y
sudo systemctl restart php-fpm

Tanpa ini, php artisan reverb:start gagal jalan dengan error class/function pcntl_* atau posix_* tidak ditemukan. Command install lain di dokumen ini (apt install ...) tinggal ganti jadi dnf install ... (nama paket bisa beda sedikit, misal php-fpm vs phpX.Y-fpm) kalau server memang RHEL-based.

Reverb butuh proses sendiri yang selalu nyala — bikin subdomain terpisah (ws.app.example.com) biar gampang di-proxy Nginx, dan systemd service:

/etc/systemd/system/laravelapp-reverb.service

ini
[Unit]
Description=Laravel Reverb WebSocket server
After=network.target

[Service]
User=laravelapp
WorkingDirectory=/home/laravelapp/app
ExecStart=/usr/bin/php artisan reverb:start --host=0.0.0.0 --port=8080
Restart=always

[Install]
WantedBy=multi-user.target
bash
sudo systemctl daemon-reload
sudo systemctl enable --now laravelapp-reverb

Alternatif: pakai Supervisor (bukan systemd) — kalau sudah pasang Supervisor buat queue worker di Langkah 1, Reverb bisa dijalankan lewat process manager yang sama supaya tidak perlu maintain dua sistem berbeda (systemd + Supervisor) buat proses long-running yang mirip:

/etc/supervisor/conf.d/laravelapp-reverb.conf (Rocky Linux/AlmaLinux Remi: /etc/supervisord.d/laravelapp-reverb.ini — lihat catatan path di Langkah 1)

ini
[program:laravelapp-reverb]
command=php /home/laravelapp/app/artisan reverb:start --host=0.0.0.0 --port=8080
directory=/home/laravelapp/app
autostart=true
autorestart=true
user=laravelapp
numprocs=1
redirect_stderr=true
stdout_logfile=/home/laravelapp/app/storage/logs/reverb.log
bash
sudo supervisorctl reread
sudo supervisorctl update
sudo supervisorctl start laravelapp-reverb

numprocs=1 (bukan 2 seperti queue worker) — Reverb itu satu server WebSocket yang pegang koneksi persisten, menjalankan lebih dari satu proses di port yang sama akan bentrok, beda dari queue worker yang memang didesain paralel. Kalau pakai Supervisor, jangan buat laravelapp-reverb.service di systemd juga — pilih salah satu, dua process manager yang sama-sama coba start proses yang sama di port yang sama akan tabrakan.

Nginx — WebSocket butuh header Upgrade/Connection khusus, koneksi HTTP biasa tidak cukup:

nginx
server {
    listen 80;
    server_name ws.app.example.com;

    location / {
        proxy_pass http://127.0.0.1:8080;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "upgrade";
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
    }
}
bash
sudo ln -s /etc/nginx/sites-available/ws-app /etc/nginx/sites-enabled/
sudo nginx -t && sudo systemctl reload nginx
sudo certbot --nginx -d ws.app.example.com   # pasang HTTPS di subdomain ini juga — lihat deploy-laravel.md

Setelah subdomain-nya HTTPS, update .env: REVERB_HOST=ws.app.example.com, REVERB_PORT=443, REVERB_SCHEME=https — dan value yang sama di sisi frontend (config Laravel Echo, biasanya VITE_REVERB_*).

3. Task Scheduler (cron)

Scheduler Laravel ($schedule->... di kode) butuh satu entri cron yang manggil schedule:run tiap menit — jadwal sebenarnya didefinisikan di kode, bukan di crontab. Pasang di crontab milik laravelapp (bukan root), konsisten sama model 1-user-per-project:

bash
sudo -u laravelapp crontab -e

Tambahkan baris:

* * * * * cd /home/laravelapp/app && php artisan schedule:run >> /dev/null 2>&1

Cek jadwal yang terdaftar & kapan berikutnya jalan tanpa nunggu cron:

bash
sudo -iu laravelapp
cd app
php artisan schedule:list
php artisan schedule:run   # jalankan manual sekali buat tes
exit