[英]How to inspect a closure in php?
I have a function that is being passed a Closure.我有一个正在传递闭包的函数。 I want to find out the name of the method that closure is derived from.
我想找出闭包派生自的方法的名称。 When I call print_r, it outputs this:
当我调用print_r时,它输出:
Closure Object
(
[static] => Array
(
[listener] => Event_Subscriber_Calq@vendor_product_created
[container] => Illuminate\Foundation\Application Object
...
How do I acess that listener value?我如何访问该侦听器值? I tried ->static, ::$static, getStatic(), I can't think of any way to get the value.
我试过 ->static、::$static、getStatic(),我想不出任何方法来获取值。
Currently, my plan is to use output buffering to capture the output from a var_dump.目前,我的计划是使用输出缓冲来捕获 var_dump 的输出。 I can't use print_r for this, because the closure contains a reference to and object that references itself, and print_r takes ages to handle the recursion.
我不能为此使用 print_r,因为闭包包含对引用自身的对象的引用,而 print_r 需要很长时间来处理递归。 I also can't use var_export, because it does not include the value I want in the output.
我也不能使用 var_export,因为它没有在输出中包含我想要的值。 So, this is my solution:
所以,这是我的解决方案:
ob_start();
var_dump($closure);
$data = ob_get_clean();
$data = preg_replace('#^([^\n]*\n){4}#', '', $data);
$data = preg_replace('#\n.*#', '', $data);
$data = preg_replace('#.*string.[0-9]+. "(.*)".*#', '\1', $data);
list($class, $method) = explode('@', $data);
Which is horrible.这是可怕的。 Is there another way to do this?
有没有另一种方法可以做到这一点? Maybe using reflection?
也许使用反射?
I know this post is old, but in case someone is looking for info, you need to use ReflectionFunction:我知道这篇文章很旧,但如果有人在寻找信息,你需要使用 ReflectionFunction:
$r = new ReflectionFunction($closure);
var_dump($r, $r->getStaticVariables(), $r->getParameters());
Regards, Alex问候,亚历克斯
In a recent project, I decided on a declarative approach by using a wrapper class.在最近的一个项目中,我决定采用一种使用包装类的声明式方法。 The class allows setting a freeform string describing the callback's origin, and can be used as a direct replacement for the closure, as it implements the
__invoke()
method.该类允许设置描述回调源的自由格式字符串,并且可以用作闭包的直接替换,因为它实现了
__invoke()
方法。
Example:例子:
use ClosureTools;
$closure = new NamedClosure(
function() {
// do something
},
'Descriptive text of the closure'
);
// Call the closure
$closure();
To access information on the closure:要访问有关关闭的信息:
if($closure instanceof NamedClosure) {
$origin = $closure->getOrigin();
}
Since the origin is a freeform string, it can be set to whatever is useful to identify the closure depending on the use case.由于原点是自由形式的字符串,因此可以根据用例将其设置为对识别闭包有用的任何内容。
Here is the class skeleton:这是类骨架:
<?php
declare(strict_types=1);
namespace ClosureTools;
use Closure;
class NamedClosure
{
/**
* @var Closure
*/
private $closure;
/**
* @var string
*/
private $origin;
/**
* @param Closure $closure
* @param string $origin
*/
public function __construct(Closure $closure, string $origin)
{
$this->closure = $closure;
$this->origin = $origin;
}
/**
* @return string
*/
public function getOrigin() : string
{
return $this->origin;
}
public function __invoke()
{
return call_user_func($this->closure, func_get_args());
}
}
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.