在工作链“结束”后触发事件

时间:2019-10-01 14:13:48

标签: php laravel laravel-5.8

我在下面的监听器中名为ProcessDocumentFields。我的侦听器类实现了ShouldQueue

在这种情况下,我使用如下的withChain方法解雇了两个作业:

ParseFieldContent::withChain([
        new ParseFieldRules($event->document, $fields),
])->dispatch($event->document, $fields);

现在,我想有条件地触发一个事件,该事件最终会触发另一个工作。

问题是,两个作业(ParseFieldContentParseFieldRules)必须都已完成运行。

#If below is true, fire off
if ($event->document->stream->settings()->get('field_routing')) {
   event(new DocumentDefaultRulesWasProcessed($event->documents));
}

上述事件将触发相同的两个作业,但是我必须先做一些其他检查:

#EventServiceProvider.php
DocumentDefaultRulesWasProcessed::class => [
     ProcessDocumentRouteFields::class,
],

在我的ProcessDocumentRouteFields里面,我有

foreach ($event->routes as $route) {
        if ($this->assertIfRouteFieldsShouldBeHandled($route, $event->document)) {
            ParseFieldContent::withChain([
                new ParseFieldRules($event->document, $route->fields, false),
            ])->dispatch($event->document, $route->fields);
        }
}

正如您在上面看到的,我运行两个相同的作业(ParseFieldContentParseFieldRules)-但前提是某个断言为真。

我的问题是:如何确保放置在ProcessDocumentFields中的作业先运行,然后在触发``事件时,运行ProcessDocumentRouteFields中的作业?

1 个答案:

答案 0 :(得分:0)

首先想到的是,您可以通过缓存或DB设置某种指示器,该指示器用于检查ProcessDocumentFields作业是否正在处理/正在运行。

然后,在您的ProcessDocumentRouteFields中,检查作业是否仍在处理/运行中。

缓存方法类似于:

if (cache('processing_job')) {
    return;
}

foreach ($event->routes as $route) {
        if ($this->assertIfRouteFieldsShouldBeHandled($route, $event->document)) {
            ParseFieldContent::withChain([
                new ParseFieldRules($event->document, $route->fields, false),
            ])->dispatch($event->document, $route->fields);
        }
}

请注意,在缓存时,必须将其设置为足够的时间来执行作业。

cache('processing_job', true, now()->addMinutes(20));

然后,您可以在所有操作完成后删除键/值对(放置在作业脚本的末尾):

Cache::forget('processing_job');

此后,下次执行缓存检查时,缓存助手将返回false并处理其他作业。

我希望这会有所帮助。