我扩展了基本的Eloquent'Collection
类如下:
class BoogerCollection extends 'Illuminate'Database'Eloquent'Collection {
// Metadata used by my collection
protected $some_array = [];
public function setArray(){
$this->some_array = [1,2,3];
}
public function getArray(){
return $this->some_array;
}
}
所以,下面的工作如预期:
$collection = new BoogerCollection();
$collection->setArray();
print_r($collection->getArray()); // Prints out Array ( [0] => 1 [1] => 2 [2] => 3 )
但是,如果我对集合执行某些操作,返回该集合的修改副本,则此元数据丢失:
// Perform some operation on the collection that makes a copy
$collection = $collection->reverse();
print_r($collection->getArray()); // Prints out Array ( )
所以我的$some_array
成员没有被复制。我深入研究了Eloquent'Collection
和Support'Collection
的代码,看起来这些方法都是通过直接从Collection的项目的内部表示构造它们来创建新的Collection的:
在Eloquent的Support'Collection
:
public function reverse()
{
// $this->items is the Collection's internal representation of the collection of items
return new static(array_reverse($this->items));
}
这是否意味着要复制我的元数据数组,我必须覆盖每一个方法?
扩展Eloquent
的Collection
类并不意味着Eloquent
将使用它来返回模型集合。现在,Eloquent
将坚持它的Collection
类,当返回一个集合时,它是Illuminate'Database'Eloquent'Collection
。如果您查看Illuminate'Database'Eloquent'Builder
的代码,您将看到返回集合(get()
, findMany()
等)的方法将调用所提供模型的newCollection()
方法,该方法反过来返回Illuminate'Database'Eloquent'Collection
的实例,而不是您新创建的子类。
你的代码:$collection = new BoogerCollection();
工作,因为你是一个实例化你的类。但是当做像MyModel::all()
这样的事情时,不会返回您的BoogerCollection
类,因为Eloquent
将选择它想要返回的Collection
类,现在它坚持使用Illuminate'Database'Eloquent'Collection
。