我正在尝试查找与 a 表中的一行相关联的 c 表(请参阅数据库架构)中的所有行。由2个透视表连接,每个透视表具有 n:m 关系。
数据库架构:http://i.stack.imgur.com/t6HbB.png
以下是我定义关系的方式:
In model A:
$this->belongsToMany("App\B");
In Model B:
$this->belongsToMany("App\A");
$this->belongsToMany("App\C");
In model C:
$this->belongsToMany("App\B");
我已经通过将方法 getC 添加到 A Eloquent模型中来实现目标:
public function getC() {
$cCollection = new Collection();
$this->b()->get()->each(function($b) use (&$cCollection){
$b->c()->get()->each(function($c) use (&$cCollection) {
$cCollection->add($c);
});
});
return $cCollection;
}
它完美无缺,但它不符合我的要求。如果我构建一个新的集合,我无法对 C 表中的行进行分页等。如果有数千行,它也会很重。
如果我尝试做这样的事情:
A::findOrFail($id)->b
我收到 B 的集合,但我无法直接获得所有 C 。如果我迭代 B 的集合:
A::findOrFail($id)->b->each(function($b){
$b->c();
});
我得到所有 C ,但我无法直接访问 C Eloquent,我无法对其进行计数,分页等等。
有没有其他方法可以做这样的事情?
A::findOrFail($id)->b->c->paginate(n);
A::findOrFail($id)->b->c->count();
A::findOrFail($id)->b->c->all();
etc...
答案 0 :(得分:1)
供参考 - 其作者也在LARAVEL.IO接受了同样的答案。
摘录:
你需要的是一个"有很多很多"关系,但laravel不支持它。
以下是关于它的旧帖子:hasManyThrough with Many-To-Many。
人们已经提出了一些解决方法,我可以为您提供另一个我认为非常干净的解决方法。它是在模型C
中嵌套whereHas的范围模型C -
public function scopeHasAViaB($query, $ids) {
if (empty($ids)) {
return new \Illuminate\Database\Eloquent\Collection();
}
return $query->whereHas('b', function ($query) use ($ids) {
$query->whereHas('a', function ($query) use ($ids) {
$query->whereIn('id', $ids);
});
});
}
- 控制器代码 -
$modelAkeys = [1,2];
$cc = ModelC::HasAViaB($modelAKeys)->paginate(10);