渴望加载单个多对多关系

时间:2017-09-21 20:11:02

标签: php laravel laravel-4.2

我有两个模型通过数据透视表与额外的列连接以跟踪数量

class Item extends Eloquent {
    public function containers()
    {
        return $this->belongsToMany('Container', 'items_containers', 'item_id', 'container_id')->withPivot(['quantity']);
    }
}

class Container extends Eloquent { 
    public function items() {
        return $this->belongsToMany('Item', 'items_containers', 'container_id', 'item_id')->withPivot(['quantity']);
    }
}

我订单的第三个模型:

class OrderItem extends Eloquent {
    public function originalItem()
    {
        return $this->hasOne('Item', 'id', 'item_id');
    }
    public function container() {
        return $this->hasOne('Container', 'id', 'container_id');
    }

}

我想要的是能够在急切加载OrderItem模型时从数据透视表中获取特定数据,因此我只获得item_idcontainer_id匹配订单上的数量的数量项目。

OrderItems::whereOrderId($orderId)
   ->with(['originalItem', 'container', '???'])
   ->get();

在OrderItem上指定关系或用with加载它的最佳方法是什么?

2 个答案:

答案 0 :(得分:2)

以下内容将返回您想要的内容:

$orders = \App\OrderItem::select('item_orders.*', 'items_containers.quantity as quantity')->with('item', 'container')
    ->leftJoin('items_containers', function ($join) {
        $join->on('items_containers.item_id', 'item_orders.item_id')
            ->where('items_containers.container_id', \DB::raw('item_orders.container_id'));
    })
    ->get();

然后您可以轻松获得数量。

$orders->first()->quantity;

那就是它。

答案 1 :(得分:1)

Morteza Rajabi让我走上正轨的主要道具。第一个关键是获取特定关系,因为虽然Items和Containers是多对多关系,但OrderItem与Item和Container都有一对一的关系。为了获得特定的关系数量,我必须创建一个指定它的属性:

public function getItemContainerQtyAttribute() {
    if($this->item_id && $this->container_id) {
        return $this->depoItem->containers()->where('items_containers.container_id', $this->container_id)->first()->pivot->quantity;
    }
    return null;
}

item_id和container_id检查是因为这是正在进行的工作,并且OrderItems并不总是正确创建,并且某些项目没有指定容器。

下一步是使用Eloquent中的appends属性自动加载它:

protected $appends = ['item_container_qty'];

现在每当我加载$item = OrderItems::whereOrderId($order_id)->get();时,它都会自动加载数据透视数量。