Laravel Workflow 扇出扇入,并发处理pdf的demo

本来想存草稿的,不小心按回车就发布出去了

medium.com/@rlmc/laravel-workflow-...

任务链 是一种工作流设计模式,涉及一系列活动的顺序执行,一个活动的输出有可能成为链中下一个活动的输入。这种模式经常被用来创建一个线性的、按部就班的流程来完成一项任务。
Chaining is a workflow design pattern that involves the sequential execution of a series of activities, with the output of one activity potentially serving as the input to the next activity in the chain. This pattern is often used to create a linear, step-by-step process for completing a task.

Laravel Workflow: Job Chaining vs. Fan-out/Fan-in
chaining

相比之下,扇出/扇入模式涉及到将一个任务划分为更小的子任务,然后将这些子任务的结果结合起来,产生最终结果。这种模式经常被用来并行化一个任务,并通过利用多个队列工作者的力量来提高其性能。

In contrast, the fan-out/fan-in pattern involves dividing a task into smaller sub-tasks and then combining the results of those sub-tasks to produce the final result. This pattern is often used to parallelize a task and improve its performance by leveraging the power of multiple queue workers.

Laravel Workflow: Job Chaining vs. Fan-out/Fan-in
fan-out/fan-in

有两个阶段:扇出和扇入。
There are two phases: fan-out and fan-in.

在扇出阶段,工作流程将主要任务分为较小的子任务,并将每个子任务分配给不同的活动。在扇入阶段,工作流程收集各活动的结果,并将它们结合起来,产生最终结果。
In the fan-out phase, the workflow divides the main task into smaller sub-tasks and assigns each of those sub-tasks to a different activity. In the fan-in phase, the workflow collects the results of the activities and combines them to produce the final result.

This article is part of a series on Larvel Workflow, a durable workflow engine that allows users to write long running persistent distributed workflows (orchestrations) in PHP powered by Laravel Queues. Inspired by Temporal and Azure Durable Functions.

下面的工作流程代表了一个扇出/扇入模式的简单例子,其中多个活动被平行执行,然后它们的结果被合并在一起。
The below workflow represents a simple example of a fan-out/fan-in pattern in which multiple activities are executed in parallel and their results are then merged together.

该工作流程将创建PDF的任务划分为多个活动,每个活动负责渲染文档的一个页面。一旦单个页面被渲染,工作流程的扇入阶段将渲染的页面合并成一个单一的PDF文档。
The workflow divides the task of creating a PDF into activities, with each activity responsible for rendering a single page of the document. Once the individual pages have been rendered, the fan-in phase of the workflow combines the rendered pages into a single PDF document.

<?php

namespace App\Workflows\BuildPDF;

use Workflow\ActivityStub;
use Workflow\Workflow;

class BuildPDFWorkflow extends Workflow
{
    public function execute()
    {
        $page1 = ActivityStub::make(ConvertURLActivity::class, 'https://example.com/');
        $page2 = ActivityStub::make(ConvertURLActivity::class, 'https://example.com/');

        $pages = yield ActivityStub::all([$page1, $page2]);

        $result = yield ActivityStub::make(MergePDFActivity::class, $pages);

        return $result;
    }
}

并行渲染页面然后合并的工作流
workflow to render pages in parallel and then merge them

The ConvertURLActivity is passed a URL as an argument, and it converts the contents of that URL into a PDF document. Because two separate activities are created, this results in the execution of two instances of ConvertURLActivity in parallel.

<?php

namespace App\Workflows\BuildPDF;

use Illuminate\Support\Facades\Http;
use Workflow\Activity;

class ConvertURLActivity extends Activity
{
    public function execute($url)
    {
        $fileName = uniqid() . '.pdf';

        Http::withHeaders([
            'Apikey' => 'YOUR-API-KEY-GOES-HERE',
        ])
        ->withOptions([
            'sink' => storage_path($fileName),
        ])
        ->post('https://api.cloudmersive.com/convert/web/url/to/pdf', [
            'Url' => $url,
        ]);

        return $fileName;
    }
}

activity that uses Cloudmersive API to convert URL to PDF

Next, the BuildPDFWorkflow uses ActivityStub::all to wait for both ConvertURLActivity instances to complete. This is an example of the fan-in part of the fan-out/fan-in pattern, as it collects the results of the parallel activities and combines them into a single array of PDF files.

Finally, the BuildPDFWorkflow executes theMergePDFActivity, which is passed the array of PDFs that were generated by the ConvertURLActivity instances, and merges them into a single PDF document.

<?php

namespace App\Workflows\BuildPDF;

use setasign\Fpdi\Fpdi;
use Workflow\Activity;

class MergePDFActivity extends Activity
{
    public function execute($pages)
    {
        $fileName = uniqid() . '.pdf';

        $pdf = new Fpdi();

        foreach ($pages as $page) {
            $pdf->AddPage();
            $pdf->setSourceFile(storage_path($page));
            $pdf->useTemplate($pdf->importPage(1));
        }

        $pdf->Output('F', storage_path($fileName));

        foreach ($pages as $page) {
            unlink(storage_path($page));
        }

        return $fileName;
    }
}

activity to merge all the pages into a single PDF

This is what the final PDF looks like…

Laravel Workflow: Job Chaining vs. Fan-out/Fan-in
both pages have been merged into a single PDF

Overall, using the fan-out/fan-in pattern in this way can significantly reduce the time it takes to create a PDF document, making the process more efficient and scalable.

Thanks for reading!

本作品采用《CC 协议》,转载必须注明作者和本文链接
CV专员在静静的抄你码
《L05 电商实战》
从零开发一个电商项目,功能包括电商后台、商品 & SKU 管理、购物车、订单管理、支付宝支付、微信支付、订单退款流程、优惠券等
《G01 Go 实战入门》
从零开始带你一步步开发一个 Go 博客项目,让你在最短的时间内学会使用 Go 进行编码。项目结构很大程度上参考了 Laravel。
讨论数量: 0
(= ̄ω ̄=)··· 暂无内容!

讨论应以学习和精进为目的。请勿发布不友善或者负能量的内容,与人为善,比聪明更重要!