Lavavel5.5源代码 - Pipeline

Posted xiaoyaogege

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了Lavavel5.5源代码 - Pipeline相关的知识,希望对你有一定的参考价值。

<?php

class Pipeline
{

    protected $passable;
    protected $pipes = [];
    protected $method = ‘handle‘;

    public function send($passable)
    {
        $this->passable = $passable;

        return $this;
    }

    public function through($pipes)
    {
        $this->pipes = is_array($pipes) ? $pipes : func_get_args();

        return $this;
    }

    public function then(Closure $destination)
    {
        $pipeline = array_reduce(
            array_reverse($this->pipes), $this->carry(), $this->prepareDestination($destination)
        );

        return $pipeline($this->passable);
    }

    protected function prepareDestination(Closure $destination)
    {
        return function ($passable) use ($destination) {
            return $destination($passable);
        };
    }

    protected function carry()
    {
        return function ($stack, $pipe) { // $stack === 下一个目标函数,$pipe == 数组项
            return function ($passable) use ($stack, $pipe) {
                if (is_callable($pipe)) {
                    // If the pipe is an instance of a Closure, we will just call it directly but
                    // otherwise we‘ll resolve the pipes out of the container and call it with
                    // the appropriate method and arguments, returning the results back out.
                    return $pipe($passable, $stack);
                } elseif (!is_object($pipe)) {
//                    list($name, $parameters) = $this->parsePipeString($pipe);
//
//                    // If the pipe is a string we will parse the string and resolve the class out
//                    // of the dependency injection container. We can then build a callable and
//                    // execute the pipe function giving in the parameters that are required.
//                    $pipe = $this->getContainer()->make($name);
//
//                    $parameters = array_merge([$passable, $stack], $parameters);
                    $pipe = new $pipe;
                    $parameters = array_merge([$passable, $stack], []);
                } else {
                    // If the pipe is already an object we‘ll just make a callable and pass it to
                    // the pipe as-is. There is no need to do any extra parsing and formatting
                    // since the object we‘re given was already a fully instantiated object.
                    $parameters = [$passable, $stack];
                }

                return method_exists($pipe, $this->method)
                    ? $pipe->{$this->method}(...$parameters)
                    : $pipe(...$parameters);
            };
        };
    }

}

class FooOneMiddleware
{
    public function handle($request, Closure $next)
    {
        echo __METHOD__.":".$request.PHP_EOL;
        return $next($request);
    }
}


class FooTwoMiddleware
{
    public function handle($request, Closure $next)
    {
        echo __METHOD__.":".$request.PHP_EOL;
        return $next($request);
    }
}

/*
    function array_reduce($array, $callback, $initial=null)
    {
        $acc = $initial;
        foreach($array as $a){
            $acc = $callback($acc, $a);
        }
        return $acc;
    }
 */
{
    $middleware = [
        FooOneMiddleware::class,
        FooTwoMiddleware::class
    ];
    $then = function () {
        return ‘this is output...‘.PHP_EOL;
    };
    $result = (new Pipeline())
        ->send(‘this is input‘)
        ->through($middleware)
        ->then($then);
    echo $result;
}

  

以上是关于Lavavel5.5源代码 - Pipeline的主要内容,如果未能解决你的问题,请参考以下文章

Lavavel5.5源代码 - 限流工具

Lavavel5.5源代码 - RedisQueue是怎么实现

Lavavel5.5源代码 - RedisQueue是怎么实现

Opengl_入门学习分享和记录_01_Graphics Pipeline(图形渲染管线)

Pipeline流水线项目构建

持续交付实践-pipeline 使用之 MultiBranch Pipeline