chefhasteeth / pipeline
Requires
- php: ^8.1.0
- laravel/framework: ^9.0|^10.0|^11.0
Requires (Dev)
- friendsofphp/php-cs-fixer: ^3.8
- nunomaduro/collision: ^6.2|^8.0
- orchestra/testbench: ^7.5|^9.0
- phpunit/phpunit: ^9.5|^10.5
- squizlabs/php_codesniffer: ^3.6
README
安装
通过composer安装
composer require chefhasteeth/pipeline
管道有哪些用途?
管道允许您通过一系列管道传递数据以执行一系列操作。每个管道都是一个可调用的代码片段:一个可调用的类、一个闭包等。由于每个管道独立地对数据进行操作(管道不知道或不在乎彼此),这意味着您可以轻松地组合复杂的流程,这些流程也是可重用的操作,并且非常容易测试——因为它们是相互独立的。
是什么让它变得如此强大?
如果Laravel是一个“内置电池”的PHP框架,那么这个包可以被认为是Illuminate\Pipeline\Pipeline
类的“内置电池”版本。它与Laravel的管道保持(主要是)兼容,但也有一些差异和新增功能。
例如,您注意到上面的withTransaction()
方法吗?这将告诉管道我们希望在数据库事务中运行这个操作,它将自动提交或回滚,具体取决于管道是否成功或失败。它还附带一个特性,提供了一个pipeThrough()
方法,可以自动将实现它的对象通过管道传递。
有哪些差异?
在Laravel的Pipeline
类中,管道本质上是接收两个参数的可调用对象:$passable
,这是传递给管道的数据,以及一个$next
回调,它调用下一个管道。
为了使我的管道可以从任何地方轻松使用,而不仅仅是管道中。例如,这可以是一个出现在管道中的GenerateThumbnail
动作,但也可能出现在cron作业中。换句话说,我不想为了满足那个$next
参数而向类或函数传递一个空的闭包。
这是这个包与Laravel的Pipeline
之间最大的区别:当前管道的输出是下一个管道的输入。
将管道发送到管道中
在配置管道时,您可以将类字符串数组、可调用的对象、闭包、具有handle()
方法的对象或任何其他通过is_callable()
的类型发送到管道。
use Chefhasteeth\Pipeline\Pipeline; class RegisterController { public function store(StoreRegistrationRequest $request) { return Pipeline::make() ->send($request->all()) ->through([ RegisterUser::class, AddMemberToTeam::class, SendWelcomeEmail::class, ]) ->then(fn ($data) => UserResource::make($data)); } }
另一种方法是在数据对象上实现这个特性。(如果您真的想的话,甚至可以在您的FormRequest
对象上实现。)
use Chefhasteeth\Pipeline\Pipable; class UserDataObject { use Pipable; public string $name; public string $email; public string $password; // ... } class RegisterController { public function store(StoreRegistrationRequest $request) { return UserDataObject::fromRequest($request) ->pipeThrough([ RegisterUser::class, AddMemberToTeam::class, SendWelcomeEmail::class, ]) ->then(fn ($data) => UserResource::make($data)); } }
为了与Laravel的Pipeline
类保持兼容,through()
方法可以接受一个可调用对象的单个数组或多个参数,其中每个参数都是之前列出的可调用类型之一。然而,pipeThrough()
特性方法只接受一个数组,因为它还有一个可选的第二个参数。
使用数据库事务
当您想在管道中使用数据库事务时,方法将根据您是使用特性还是Pipeline
类而有所不同。
使用Pipeline
类
Pipeline::make()->withTransaction()
withTransaction()
方法会告诉管道使用事务。当您调用 then()
或 thenReturn()
方法时,在执行管道之前会开始数据库事务。如果在管道中遇到异常,事务将被回滚,因此不会将任何数据提交到数据库。假设管道成功完成,则事务将被提交。
当使用该特质时,您可以向 pipeThrough()
方法传递第二个参数。
$object->pipeThrough($pipes, withTransaction: true);
测试
composer test
许可证
MIT 许可证 (MIT)。有关更多信息,请参阅 LICENSE。