mcpField
L
laravel-queues

laravel-queues

github.com/asyrafhussin開発95712 回インストール9 週間前に更新
リポジトリ

laravel-queues について

Laravel 13 のキュー開発と運用を支援するスキルです。設定、ジョブ設計、再試行、スケーリング、テストを扱う20のルールで、本番負荷で問題になりやすい実装を監査します。

主な機能

  1. 016 分野、20 のキュールール
  2. 02キュー設定とジョブの確認
  3. 03再試行と失敗処理の点検
  4. 04ワーカーの拡張と再起動
  5. 05バッチ、チェーン、テストの指針

活用シーン

  1. 01バックグラウンドジョブの設計・レビュー
  2. 02停止または失敗を繰り返すジョブの調査
  3. 03Redis キューワーカーの設定
  4. 04キューテストや Horizon 導入の検討

インストール

コマンドをコピーしてターミナルで実行します。

$npx skills add https://github.com/asyrafhussin/agent-skills --skill laravel-queues

インストール後、Claude Code で/laravel-queuesを入力して読み込まれたか確認します。

同梱ファイル

SKILL.md と一緒にインストールされる参考資料やスクリプト。

AGENTS.md
metadata.json
README.md
rules/
_sections.md
_template.md
bus-batch-failure-handling.md
bus-batch-vs-chain.md
bus-chunking-large-sets.md
config-after-commit.md
config-driver-choice.md
config-failed-storage.md
design-constructor-vs-handle.md
design-idempotency.md
design-pass-ids-not-models.md
design-shouldqueue.md
ops-horizon-when.md
ops-queue-fake.md
ops-schedule-queued-jobs.md
retry-fail-on-timeout.md
retry-failed-method.md
retry-transient-vs-permanent.md
retry-tries-and-backoff.md
scaling-multi-queue-priority.md
scaling-supervisor-config.md
scaling-worker-recycling.md

詳細

Laravel のキューとジョブ

Laravel 13(MySQL + Redis)向けの、本番環境に適したキューパターンです。ドライバーの選択、ジョブの設計、リトライと失敗への対応、ワーカーのスケーリング、バッチ処理とチェーン処理、テストを扱う6つのカテゴリーに、20のルールを収録しています。コードレビューを通過しても負荷がかかると問題になる失敗パターンを対象としています。たとえば、リトライ時に気付かないまま再ディスパッチされる、シリアライズ後にモデルが古い状態になる、決済ジョブに冪等性がない、ワーカーでメモリリークが発生する、「ShouldQueue を付け忘れて、本番環境でリクエストに12秒かかる」といった問題です。

メタデータ

  • バージョン: 1.0.0
  • 対象範囲: PHP / Laravel 13 + MySQL + Redis(キュー)、Horizon は任意
  • ルール数: 6つのカテゴリーに20のルール
  • ライセンス: MIT

使い方

ユーザーから「このバックグラウンドジョブを設計して」「キュー設定を監査して」「このジョブが実行されない理由は?」「キューに関する質問」などを受けた場合は、このスキルのルールをチェックリストとして、該当ファイル(ジョブクラス、config/queue.php、config/horizon.php、Supervisor の設定、ディスパッチ呼び出し箇所)を確認してください。

監査モードでは、ルールごとに次の判定を出力してください。

  • PASS — パターンが正しく適用されています
  • FAIL — アンチパターンが存在します(ファイル名と行番号、および修正の推奨事項を記載)
  • N/A — このコードベースには該当しません

最後に、優先度の高い修正項目のリストを示してください(決済ジョブの冪等性、ShouldQueue の付け忘れ、Supervisor の stopwaitsecs が短すぎること。本番環境で問題になりやすいのは、これらが最も一般的です)。

適用する場面

次の場合は、このスキルを参照してください。

  • 新しいバックグラウンドジョブを作成するとき(php artisan make:job)
  • ジョブクラスを追加または変更する PR をレビューするとき
  • 新しいサーバーでキューワーカーを設定するとき(Forge / Vapor / ベアサーバー)
  • config/queue.php または config/horizon.php を設定するとき
  • 停止した、ループする、または繰り返し失敗するジョブをデバッグするとき
  • dispatch()、dispatchSync()、dispatchAfterResponse()、Bus::batch()、Bus::chain() のいずれを使うか選ぶとき
  • キューテスト(Queue::fake()、Bus::fake())を追加するとき
  • Horizon を採用するかどうか判断するとき

ステップ1:キューの設定を確認する

次を調べます。

ファイル確認する内容
config/queue.phpデフォルトの接続(QUEUE_CONNECTION 環境変数)、失敗ジョブの保存先、after_commit の設定
config/horizon.php(存在する場合)Horizon の環境、バランス戦略、ワーカー数、タイムアウト
app/Jobs/*.phpジョブクラス、ShouldQueue の使用状況、tries/backoff、failed() メソッド
app/Console/Kernel.php または routes/console.phpスケジュールされたジョブ(Schedule::job(...)、withoutOverlapping)
database/migrations/*_create_failed_jobs_table.php失敗ジョブ保存用のマイグレーション、または設定における DynamoDB ドライバー
supervisor*.conf / /etc/supervisor/conf.d/ワーカープロセスの管理、numprocs、--max-time、stopwaitsecs

一般的な構成:

スタックキュードライバー失敗ジョブ用ドライバーワーカー管理
小規模な Laravel + MySQLdatabasedatabaseSupervisor(または systemd)
本番環境の Laravel + Redisredisdatabase(またはサーバーレス環境では dynamodb)Supervisor + Horizon
Laravel VaporsqsdynamodbVapor による管理

優先度別のルールカテゴリー

優先度カテゴリー影響度プレフィックス
1ドライバーと設定CRITICALconfig-
2ジョブ設計CRITICALdesign-
3リトライと失敗HIGHretry-
4スケーリングとワーカーHIGHscaling-
5バッチ処理とチェーン処理HIGHbus-
6テストと運用MEDIUMops-

クイックリファレンス

1. ドライバーと設定(CRITICAL)
  • config-driver-choice — 小規模なアプリには database、本番環境での大規模運用には redis、Laravel Vapor には sqs を使用します
  • config-after-commit — 未コミットの DB 行を参照するジョブがディスパッチされないよう、after_commit: true に設定します
  • config-failed-storage — failed_jobs テーブル(または Vapor では DynamoDB)が必要です。保持期間とクリーンアップを設定してください
2. ジョブの設計(最重要)
  • design-shouldqueue — すべての非同期ジョブで ShouldQueue を実装する必要があります(本番環境で最も多いバグ:実装を忘れるとジョブが同期的に実行されます)
  • design-pass-ids-not-models — コンストラクターには ID を渡し、handle() で再取得します。古くなったモデルや肥大化したシリアライズ済みペイロードを避けられます
  • design-idempotency — 決済、外部 API、「リソースの作成」を行うジョブは、2 回実行されても安全である必要があります(ShouldBeUnique、冪等性キー、一意制約のある DB)
  • design-constructor-vs-handle — コンストラクターはディスパッチ時(同期)に実行され、handle() はワーカー上で実行されます。コンストラクター内で DB への書き込みや HTTP 呼び出しを行わないでください。
3. 再試行と失敗(重要)
  • retry-tries-and-backoff — 両方を設定します。指数的な遅延には #[Backoff([1, 5, 30])] を使用します。デフォルトの 3 回では、一時的な障害に対して通常は不十分です
  • retry-failed-method — 恒久的な失敗への対応(通知、返金、失敗としてマーク)には、failed(Throwable $e) を実装します
  • retry-transient-vs-permanent — 一時的なエラー(レート制限、ネットワーク障害)には release($delay) を使用し、恒久的なエラーには例外をスローします
  • retry-fail-on-timeout — ハングしたジョブですべての試行が無駄になるのを避けるには、#[FailOnTimeout] を使用します
4. スケーリングとワーカー(重要)
  • scaling-supervisor-config — Supervisor(または systemd)でワーカーを管理します。stopwaitsecs > timeout とし、ワーカーを再起動するには --max-time=3600 を指定します
  • scaling-multi-queue-priority — SLA が重要なジョブには high/default/low のキューレーンを使用します。--queue=high,default,low
  • scaling-worker-recycling — 長時間稼働するワーカーのメモリーリークを抑えるには、--max-jobs と --max-time を使用します
5. バッチ処理とチェーン処理(重要)
  • bus-batch-vs-chain — 並列処理と進捗追跡には Bus::batch、厳密な順次処理には Bus::chain を使用します
  • bus-batch-failure-handling — 障害許容型のバッチには allowFailures() を使用し、then/catch/finally コールバックを活用します
  • bus-chunking-large-sets — 1000 件以上の項目を処理する場合は、項目ごとに 1 つのジョブを作成するのではなく、Bus::batch(...) でチャンクに分割します
6. テストと運用(中程度)
  • ops-queue-fake — テストでは Queue::fake()/Bus::fake() を使用します。assertDispatched、assertPushed、assertChained、assertBatched を利用できます
  • ops-schedule-queued-jobs — Schedule::job(new X)->everyMinute() はジョブをキューに追加します。安全のため、withoutOverlapping() と組み合わせます
  • ops-horizon-when — 複数のスーパーバイザーを使用する Redis 環境では Horizon を導入します。database キューや単一ワーカーの構成には適していません

必須パターン

最小限のジョブクラス(Laravel 13)
<?php

namespace App\Jobs;

use App\Models\Order;
use Illuminate\Bus\Queueable;
use Illuminate\Contracts\Queue\ShouldQueue;
use Illuminate\Foundation\Bus\Dispatchable;
use Illuminate\Queue\Attributes\Backoff;
use Illuminate\Queue\Attributes\FailOnTimeout;
use Illuminate\Queue\InteractsWithQueue;
use Illuminate\Queue\SerializesModels;
use Throwable;

#[Backoff([1, 5, 30])]
#[FailOnTimeout]
class ChargeOrder implements ShouldQueue
{
    use Dispatchable, InteractsWithQueue, Queueable, SerializesModels;

    public int $tries = 5;
    public int $timeout = 30;

    public function __construct(public readonly int $orderId) {}

    public function handle(StripeGateway $stripe): void
    {
        $order = Order::findOrFail($this->orderId);   // refetch — don't trust serialised state
        if ($order->status === 'paid') return;        // idempotency guard

        $charge = $stripe->charge($order);
        $order->markPaid($charge->id);
    }

    public function failed(Throwable $e): void
    {
        Order::find($this->orderId)?->markPaymentFailed($e->getMessage());
    }
}
ディスパッチ
ChargeOrder::dispatch($order->id);                       // default queue
ChargeOrder::dispatch($order->id)->onQueue('high');      // priority lane
ChargeOrder::dispatch($order->id)->delay(now()->addMinutes(5));
ChargeOrder::dispatchAfterResponse($order->id);          // run after HTTP response sent
Supervisor の設定(推奨)
[program:laravel-worker]
process_name=%(program_name)s_%(process_num)02d
command=php /var/www/app/artisan queue:work redis --queue=high,default,low --sleep=3 --tries=3 --max-time=3600 --backoff=3
autostart=true
autorestart=true
stopasgroup=true
killasgroup=true
user=forge
numprocs=8
redirect_stderr=true
stdout_logfile=/var/www/app/storage/logs/worker.log
stopwaitsecs=3600

重要: stopwaitsecs は最も時間のかかるジョブのタイムアウトより大きくする必要があります。そうしないと、デプロイ時に Supervisor がジョブの実行途中でプロセスを終了します。

参考資料

コンパイル済みドキュメント全文

すべてのルールを詳しく記載した完全なガイド:AGENTS.md

コメント