株式会社WR

株式会社WR

WEB TOTAL CONSULTING

Laravel Horizonでキューを可視化——非同期処理の監視と最適化
ブログ一覧へ
技術ブログ

Laravel Horizonでキューを可視化——非同期処理の監視と最適化

Laravel Horizonを導入すると、Redisキューの処理状況をブラウザでリアルタイム監視できます。失敗ジョブの確認・再実行・スループット分析まで対応しています。

Laravel Horizonとは——キューの可視化ツール

Laravel Horizonは、Laravelのキュー(Redisベース)を可視化・管理するためのダッシュボードです。ジョブの実行状況・失敗ジョブ・スループット・ワーカー状態をリアルタイムで確認できます。


インストールと設定

composer require laravel/horizon
php artisan horizon:install
php artisan migrate
// config/horizon.php
'environments' => [
    'production' => [
        'supervisor-1' => [
            'connection'  => 'redis',
            'queue'       => ['high', 'default', 'low'],
            'balance'     => 'auto',       // 負荷に応じてワーカー数を自動調整
            'minProcesses'=> 2,
            'maxProcesses'=> 10,
            'memory'      => 128,
            'tries'        => 3,
            'timeout'      => 60,
        ],
    ],
    'local' => [
        'supervisor-1' => [
            'connection'  => 'redis',
            'queue'       => ['high', 'default', 'low'],
            'balance'     => 'simple',
            'processes'   => 3,
        ],
    ],
],

キューの優先度設定

// 優先度の高い処理を 'high' キューに
Mail::to($user)->queue((new WelcomeMail($user))->onQueue('high'));

// 通常の処理は 'default' キュー
ProcessOrder::dispatch($order); // デフォルトキュー

// 低優先度の処理は 'low' キュー
GenerateReport::dispatch($report)->onQueue('low');

ジョブの設計——タイムアウト・リトライ

class ProcessOrderJob implements ShouldQueue
{
    use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;

    public int $tries   = 3;       // 最大3回リトライ
    public int $timeout = 120;     // 2分でタイムアウト
    public int $backoff = 60;      // 失敗後60秒待ってリトライ

    public function __construct(
        public readonly Order $order,
    ) {}

    public function handle(): void
    {
        // 処理
        $this->order->process();
    }

    public function failed(\Throwable $e): void
    {
        // 全リトライが失敗した場合
        Log::error("注文処理失敗: #{$this->order->id}", [
            'error' => $e->getMessage(),
        ]);

        // 管理者に通知
        Notification::send(
            User::admins()->get(),
            new JobFailedNotification($this->order, $e)
        );
    }

    /**
     * リトライするか判断する(特定のエラーは即座に失敗)
     */
    public function shouldRetry(\Throwable $e): bool
    {
        return !($e instanceof \InvalidArgumentException);
    }
}

Horizonダッシュボードへのアクセス制限

// app/Providers/HorizonServiceProvider.php
class HorizonServiceProvider extends HorizonApplicationServiceProvider
{
    protected function gate(): void
    {
        Gate::define('viewHorizon', function ($user) {
            return in_array($user->email, [
                'admin@example.com',
                'devops@example.com',
            ]);
        });
    }
}

Horizonの本番運用

# Supervisor で常時起動
php artisan horizon

# ダウンタイムなしの再起動(デプロイ後)
php artisan horizon:terminate
# Supervisor が自動的に再起動する
; /etc/supervisor/conf.d/horizon.conf
[program:horizon]
command=php /var/www/html/artisan horizon
autostart=true
autorestart=true
user=www-data
redirect_stderr=true
stdout_logfile=/var/www/html/storage/logs/horizon.log
stopwaitsecs=3600

メトリクスの確認

Horizonダッシュボード(/horizon)で確認できる主な情報:

  • スループット:1分間に処理されるジョブ数
  • 待機時間:ジョブがキューに入ってから実行されるまでの時間
  • 失敗ジョブ:失敗の理由・スタックトレース・再試行ボタン
  • ジョブ一覧:実行中・完了・失敗のジョブ一覧
  • ワーカー:稼働中のワーカー数・メモリ使用量

まとめ

Laravel Horizonはキューベースの非同期処理を可視化し、パフォーマンスのボトルネック発見・失敗ジョブの再実行を容易にします。本番環境でキューを使うなら必須のツールです。弊社ではメール送信・EC連携・スクレイピングなどの非同期処理をHorizonで監視しています。

LaravelによるWebシステム開発のご相談はお気軽にどうぞ。

Category 技術ブログ

Related Posts

関連記事

開発・技術のご相談はお気軽に

お見積りは無料です。まずはお気軽にご相談ください。

お問い合わせ →