在Eloquent模型的构造函数中创建闭包作为类变量


Creation of a closure as class variable in constructor of Eloquent Model

我正试图在Eloquent模型的构造函数中创建一个lambda样式的闭包,作为一个动态命名的类变量。

除了创建模型(也就是说,读取、更新和删除操作都很好)之外,当对象被实例化时,它工作得很好。

我可以通过在实例化对象之前显式声明类变量来解决这个问题,然而,这只是一个技巧,我需要能够动态创建类变量(作为闭包)。

以下代码有效,但如果我删除声明$public foo;

public $foo;
public function __construct() {
    $foo = 'foo';
    $this->{$foo} = function ($args) { return 'foo';};
}

我得到以下错误:

异常"ErrorException",消息为"类的对象Closure可能无法转换为中的字符串"/用户/站点//vendor/laravel/framework/src/IIlluminate/Support/helpers.php:900

就像我提到的,这只发生在创建/插入对象时(如果这听起来很模糊,很抱歉,但熟悉Laravel的人应该知道我的意思)。。。在其他情况下实例化模型(读取/更新/删除)也很好。任何可能导致问题的想法都将不胜感激!

在您的型号上覆盖setAttributegetAttribute

protected $closures = [];
public function setAttribute($key, $value)
{
    if ($value instanceof 'Closure)
    {
        $this->setClosureProperty($key, $value);
    }
    parent::setAttribute($key, $value);
}
public function getAttribute($key)
{
    if (array_key_exists($key, $this->closures)
    {
        return $this->closures[$key];
    }
    return parent::getAttribute($key);
}
public function setClosureProperty($key, 'Closure $value)
{
    $this->closures[$key] = $value;
}

这样,cloture就不会保存在attributes数组中,因此也不会保存并强制转换为字符串。