前往小程序,Get更优阅读体验!
立即前往
首页
学习
活动
专区
工具
TVP
发布
社区首页 >专栏 >Laravel5.3之Callback Type

Laravel5.3之Callback Type

作者头像
botkenni
发布2022-01-10 09:41:12
1.2K0
发布2022-01-10 09:41:12
举报
文章被收录于专栏:IT码农

说明:本文主要学习PHP的回调类型callback type,通常在使用函数进行回调时,如使用call_user_func(callback, parameters)进行回调时,需要传入回调callback,实际上有几种callback type的,在Laravel中也大量使用回调,并根据场景不同传入不同的回调类型。

开发环境:Laravel5.3 + PHP7

(Function/Static Class Method) Callback Type

Function Callback Type是把函数名作为callable类型传进去作为回调类型,形式如:(function_name, dependency)。Static Class Method Callable Type与其类似,是把类名+静态方法名传进去作为回调类型,形式如:("class_name::static_method_name",

代码语言:javascript
复制
<?php

namespace MyRightCapital\Container\Tests;

class Callback extends \PHPUnit_Framework_TestCase
{
    public function testFunctionCallback()
    {
        // Arrange
        $expected = 'container';
        
        // Actual
        $actual = call_user_func('MyRightCapital\Container\Tests\functionCallback', 'container'); // ($function_name, $dependency)
        
        // Assert
        $this->assertSame($expected, $actual);
    }
    
    public function testStaticClassMethodCallback()
    {
        // Arrange
        $expected = 'container';
        
        // Actual
        $actual = call_user_func('MyRightCapital\Container\Tests\StaticClassMethodCallback::staticClassMethod', 'container'); // ("$class_name::$static_method_name", $dependency)
        
        // Assert
        $this->assertSame($expected, $actual);
    }
}

function functionCallback($app)
{
    return $app;
}

class StaticClassMethodCallback
{
    public static function staticClassMethod($app)
    {
        return $app;
    }
}

(Class Method/Relation Class Method) Callback Type

Class Method Callback Type也是类名+静态方法名,只不过形式稍不一样,形式如:([class_name, method_name], dependency)。Relation Class Method Callback Type是可以使用父类的方法传进去作为回调,形式如:([class_name, "parent::method_name"],

代码语言:javascript
复制
    public function testClassMethodCallback()
    {
        // Arrange
        $expected = 'container';
        
        // Actual
        $actual = call_user_func([ClassMethodCallback::class, 'classMethod'], 'container'); // ([$class_name, $method_name], $dependency)
        
        // Assert
        $this->assertSame($expected, $actual);
    }
    
    public function testRelationClassMethodCallback()
    {
        // Arrange
        $expected = 'container/container';
        
        // Actual
        $actual = call_user_func([ClassMethodCallback::class, 'parent::classMethod'], 'container'); // ([$class_name, "parent::$method_name"], $dependency)
        
        // Assert
        $this->assertSame($expected, $actual);
    }
    
    
    class ClassMethodCallback extends ParentClassMethodCallback
    {
        public static function classMethod($app)
        {
            return $app;
        }
    }
    
    class ParentClassMethodCallback
    {
        public static function classMethod($app)
        {
            return $app . '/' . $app;
        }
    }

Object Method Callback Type

Object Method Callback Type是把对象方法作为参数传进去作为回调,形式如:([object, method_name],

代码语言:javascript
复制
    public function testObjectMethodCallback()
    {
        // Arrange
        $class_method_callback = new ClassMethodCallback();
        $expected = 'container';
        
        // Actual
        $actual = call_user_func([$class_method_callback, 'objectMethod'], 'container'); // ([$object, $method_name], $dependency)
        
        // Assert
        $this->assertSame($expected, $actual);
    }
    
    class ClassMethodCallback extends ParentClassMethodCallback
    {
        public static function classMethod($app)
        {
            return $app;
        }
        
        public function objectMethod($app)
        {
            return $app;
        }
    }

Closure

把Closure作为参数传进去作为回调参数这种方式在Laravel中大量使用,比如Laravel的Pipeline源码就大量使用这种方式,Pipeline的源码可看:Laravel5.3Middleware源码解析。写下PHPUnit测试看下:

代码语言:javascript
复制
    public function testClosureCallback()
    {
        // Arrange
        
        // Actual
        $actual       = call_user_func(getClosure(), 'stack', 'pipe');
        $actual_value = call_user_func($actual, 'request');
        // Assert
        $this->assertInstanceOf(\Closure::class, $actual);
        $this->assertSame('request/stack/pipe', $actual_value);
    }
    
    
    function getClosure()
    {
        return function ($stack, $pipe) {
            return function ($passable) use ($stack, $pipe) {
                return $passable . '/' . $stack . '/' . $pipe;
            };
        };
    }

最后,给出整个源码和测试结果:

代码语言:javascript
复制
<?php

namespace MyRightCapital\Container\Tests;

class Callback extends \PHPUnit_Framework_TestCase
{
    public function testFunctionCallback()
    {
        // Arrange
        $expected = 'container';
        
        // Actual
        $actual = call_user_func('MyRightCapital\Container\Tests\functionCallback', 'container'); // ($function_name, $dependency)
        
        // Assert
        $this->assertSame($expected, $actual);
    }
    
    public function testStaticClassMethodCallback()
    {
        // Arrange
        $expected = 'container';
        
        // Actual
        $actual = call_user_func('MyRightCapital\Container\Tests\StaticClassMethodCallback::staticClassMethod', 'container'); // ("$class_name::$static_method_name", $dependency)
        
        // Assert
        $this->assertSame($expected, $actual);
    }
    
    public function testClassMethodCallback()
    {
        // Arrange
        $expected = 'container';
        
        // Actual
        $actual = call_user_func([ClassMethodCallback::class, 'classMethod'], 'container'); // ([$class_name, $method_name], $dependency)
        
        // Assert
        $this->assertSame($expected, $actual);
    }
    
    public function testRelationClassMethodCallback()
    {
        // Arrange
        $expected = 'container/container';
        
        // Actual
        $actual = call_user_func([ClassMethodCallback::class, 'parent::classMethod'], 'container'); // ([$class_name, "parent::$method_name"], $dependency)
        
        // Assert
        $this->assertSame($expected, $actual);
    }
    
    public function testObjectMethodCallback()
    {
        // Arrange
        $class_method_callback = new ClassMethodCallback();
        $expected              = 'container';
        
        // Actual
        $actual = call_user_func([$class_method_callback, 'objectMethod'], 'container'); // ([$object, $method_name], $dependency)
        
        // Assert
        $this->assertSame($expected, $actual);
    }
    
    public function testClosureCallback()
    {
        // Arrange
        
        // Actual
        $actual       = call_user_func(getClosure(), 'stack', 'pipe');
        $actual_value = call_user_func($actual, 'request');
        // Assert
        $this->assertInstanceOf(\Closure::class, $actual);
        $this->assertSame('request/stack/pipe', $actual_value);
    }
}

function getClosure()
{
    return function ($stack, $pipe) {
        return function ($passable) use ($stack, $pipe) {
            return $passable . '/' . $stack . '/' . $pipe;
        };
    };
}

function functionCallback($app)
{
    return $app;
}

class StaticClassMethodCallback
{
    public static function staticClassMethod($app)
    {
        return $app;
    }
}

class ClassMethodCallback extends ParentClassMethodCallback
{
    public static function classMethod($app)
    {
        return $app;
    }
    
    public function objectMethod($app)
    {
        return $app;
    }
}

class ParentClassMethodCallback
{
    public static function classMethod($app)
    {
        return $app . '/' . $app;
    }
}

总结:本文主要总结下PHP的Callback Type,便于提高自己的代码设计能力。遇到好的技术再聊,到时见。

本文参与 腾讯云自媒体同步曝光计划,分享自作者个人站点/博客。
原始发表:2016/11/15 ,如有侵权请联系 cloudcommunity@tencent.com 删除

本文分享自 作者个人站点/博客 前往查看

如有侵权,请联系 cloudcommunity@tencent.com 删除。

本文参与 腾讯云自媒体同步曝光计划  ,欢迎热爱写作的你一起参与!

评论
登录后参与评论
0 条评论
热度
最新
推荐阅读
目录
  • (Function/Static Class Method) Callback Type
  • (Class Method/Relation Class Method) Callback Type
  • Object Method Callback Type
  • Closure
领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档