spatie/laravel-queueable-action

Laravel 的队列支持

2.15.0 2024-02-27 12:08 UTC

README

Latest Version on Packagist GitHub Workflow Status Check & fix styling Total Downloads

动作是结构化 Laravel 中业务逻辑的一种方式。此包添加了易于支持它们可排队的功能。

$myAction->onQueue()->execute();

您可以指定一个队列名称。

$myAction->onQueue('my-favorite-queue')->execute();

支持我们

我们投入了大量资源来创建 一流的开源包。您可以通过 购买我们的付费产品之一 来支持我们。

我们非常感谢您从家乡寄来明信片,说明您正在使用我们的哪个包。您可以在 我们的联系页面 上找到我们的地址。我们将所有收到的明信片发布在我们的 虚拟明信片墙上

安装

您可以通过 composer 安装此包。

composer require spatie/laravel-queueable-action

您可以选择使用以下命令发布配置文件:

php artisan vendor:publish --provider="Spatie\QueueableAction\QueueableActionServiceProvider" --tag="config"

这是发布配置文件的内容

return [
    /*
     * The job class that will be dispatched.
     * If you would like to change it and use your own job class,
     * it must extends the \Spatie\QueueableAction\ActionJob class.
     */
    'job_class' => \Spatie\QueueableAction\ActionJob::class,
];

用法

如果您想了解动作及其异步使用的推理,您应该阅读专门的博客文章:https://stitcher.io/blog/laravel-queueable-actions

您可以使用以下 Artisan 命令动态生成可排队的和同步的动作类。

php artisan make:action MyAction [--sync]

这是使用可排队的动作的示例

class MyAction
{
    use QueueableAction;

    public function __construct(
        OtherAction $otherAction,
        ServiceFromTheContainer $service
    ) {
        // Constructor arguments can come from the container.

        $this->otherAction = $otherAction;
        $this->service = $service;
    }

    public function execute(
        MyModel $model,
        RequestData $requestData
    ) {
        // The business logic goes here, this can be executed in an async job.
    }
}
class MyController
{
    public function store(
        MyRequest $request,
        MyModel $model,
        MyAction $action
    ) {
        $requestData = RequestData::fromRequest($myRequest);

        // Execute the action on the queue:
        $action->onQueue()->execute($model, $requestData);

        // Or right now:
        $action->execute($model, $requestData);
    }
}

该包还支持使用 __invoke() 方法的动作。这将被自动检测。以下是一个示例

class MyInvokeableAction
{
    use QueueableAction;

    public function __invoke(
        MyModel $model,
        RequestData $requestData
    ) {
        // The business logic goes here, this can be executed in an async job.
    }
}

使用 __invoke() 方法的动作应像上面的示例中那样添加到队列中,通过在 onQueue() 方法之后运行 execute() 方法。

$myInvokeableAction->onQueue()->execute($model, $requestData);

测试队列动作

该包在 Spatie\QueueableAction\Testing\QueueableActionFake 类中提供了一些测试断言。您可以在 PhpUnit 测试中使用它们,如下所示

/** @test */
public function it_queues_an_action()
{
    Queue::fake();

    (new DoSomethingAction)->onQueue()->execute();

    QueueableActionFake::assertPushed(DoSomethingAction::class);
}

在使用 QueueableActionFake 断言之前,不要忘记使用 Queue::fake() 来模拟 Laravel 的队列。

以下断言可用

QueueableActionFake::assertPushed(string $actionClass);
QueueableActionFake::assertPushedTimes(string $actionClass, int $times = 1);
QueueableActionFake::assertNotPushed(string $actionClass);
QueueableActionFake::assertPushedWithChain(string $actionClass, array $expextedActionChain = [])
QueueableActionFake::assertPushedWithoutChain(string $actionClass)

如果您认为其他 QueueFake 断言中缺少任何内容,请随时发送 PR。

链式调用动作

您可以通过将它们包装在 ActionJob 中来链式调用动作。

以下是具有相同参数的两个动作的示例

use Spatie\QueueableAction\ActionJob;

$args = [$userId, $data];

app(MyAction::class)
    ->onQueue()
    ->execute(...$args)
    ->chain([
        new ActionJob(AnotherAction::class, $args),
    ]);

ActionJob 以动作类 实例作为第一个参数,后面跟着动作参数的数组。

自定义标签

如果您想更改 Horizon 中显示的自定义动作的标签,可以覆盖 tags() 函数。

class CustomTagsAction
{
    use QueueableAction;

    // ...

    public function tags() {
        return ['action', 'custom_tags'];
    }
}

作业中间件

可以通过覆盖 middleware() 函数来添加动作作业通过的中间件。

class CustomTagsAction
{
    use QueueableAction;

    // ...

    public function middleware() {
        return [new RateLimited()];
    }
}

动作回退

如果您想配置 Laravel 在每个动作的基础上等待多少秒才重试遇到异常的动作,您可以在动作类上定义回退属性来这样做

class BackoffAction
{
    use QueueableAction;
    
    /**
     * The number of seconds to wait before retrying the action.
     *
     * @var array<int>|int
     */
    public $backoff = 3;
}

如果您需要更复杂的逻辑来确定动作的回退时间,您可以在动作类上定义回退方法

class BackoffAction
{
    use QueueableAction;
    
    /**
     * Calculate the number of seconds to wait before retrying the action.
     *
     */
    public function backoff(): int
    {
        return 3;
    }
}

您可以通过从回退方法返回一个回退值数组轻松配置“指数”回退。在这个例子中,第一次重试的延迟将是1秒,第二次重试的延迟是5秒,第三次重试的延迟是10秒。

class BackoffAction
{
    /**
     * Calculate the number of seconds to wait before retrying the action.
     *
     */
    public function backoff(): array
    {
        return [1, 5, 10];
    }
}

动作和作业有什么区别?

简而言之:构造函数注入提供了更大的灵活性。您可以在这里阅读深入的解释:[Laravel Queueable Actions](https://stitcher.io/blog/laravel-queueable-actions#what's-the-difference-with-jobs?!?)(外部链接)。

测试软件包

composer test

更新日志

有关最近更改的更多信息,请参阅[更新日志](https://github.com/spatie/laravel-queueable-action/blob/HEAD/CHANGELOG.md)。

贡献

有关详细信息,请参阅[贡献指南](https://github.com/spatie/.github/blob/main/CONTRIBUTING.md)。

安全

如果您发现了关于安全性的错误,请通过发送邮件至[security@spatie.be](mailto:security@spatie.be)而不是使用问题跟踪器。

鸣谢

许可证

MIT许可证(MIT)。有关更多信息,请参阅[许可证文件](https://github.com/spatie/laravel-queueable-action/blob/HEAD/LICENSE.md)。