テーブルレイアウトは次のようになります。
deals:
- id
- price
products:
- id
- name
deal_product:
- id
- deal_id
- product_id
metrics:
- id
- name
metric_product:
- id
- metric_id
- product_id
- value
products
metrics
値のピボット列と多対多の関係を持ちます。
deals
また、products
多対多の関係もあります。
を使用して製品の指標を取得できます$product->metrics
が、取引に関連するすべての製品の指標をすべて取得できるようにしたいので、次のようにします$deal->metrics
。
現在、私のDeal
モデルには次のものがあります:
public function metrics()
{
$products = $this->products()->pluck('products.id')->all();
return Metric::whereHas('products', function (Builder $query) use ($products) {
$query->whereIn('products.id', $products);
});
}
しかし、これは関係を返さないので、それを早期ロードしたり、そこから関連モデルを取得したりすることはできません。
私のユースケースでは、それらを早期にロードする必要があるため、リレーションシップ形式にする必要があります。
ご協力いただきありがとうございます!
ベストアンサー1
カスタム リレーションが必要な場合は、独自の Relation 抽象クラスを拡張して作成できます。例: BelongsToManyThought
。
しかし、Relation を実装したくない場合は、次の方法でニーズを満たすことができると思います。
App\Deal.phpでは、@thomas-van-der-veenのソリューションを組み合わせることができます。
public function metrics()
{
return Metric
::join('metric_product', 'metric.id', '=', 'metric_product.metric_id')
->join('products', 'metric_product.product_id', '=', 'products.id')
->join('deal_product', 'products.id', '=', 'deal_product.product_id')
->join('deals', 'deal_product.deal_id', '=', 'deal.id')
->where('deal.id', $this->id);
}
// you can access to $deal->metrics and use eager loading
public function getMetricsAttribute()
{
if (!$this->relationLoaded('products') || !$this->products->first()->relationLoaded('metrics')) {
$this->load('products.metrics');
}
return collect($this->products->lists('metrics'))->collapse()->unique();
}
これを参考にしてください役職ネストされた関係を簡単に使用する方法を確認します。
このソリューションは、メソッドを使用して関係を照会し、メトリック属性にアクセスするために役立ちます。