简体   繁体   English

Laravel 5.6 / Eloquent Sum 和 GroupBy 与相关表/关系

[英]Laravel 5.6 / Eloquent Sum and GroupBy with related tables/relationships

I am trying to sum a column while grouping by data within the table as well as a related table.我试图在按表中的数据以及相关表进行分组时对一列求和。

Order Table订单表

  • id ID
  • location_id location_id
  • received_date收到的日期

Order Items Table订购项目表

  • id ID
  • order_id订单编号
  • product_id产品编号
  • qty数量

Relationships关系

Order item belongs to Order订单项属于订单

public function order() : BelongsTo
{
    return $this->belongsTo(Order::class);
}

Query询问

I am looking for a result of:我正在寻找以下结果:

  • product_id (groupBy on order_items table) product_id(order_items 表上的 groupBy)
  • location_id (groupBy on orders table) location_id(订单表上的 groupBy)
  • qty (sum on order_items table)数量(order_items 表上的总和)

The following gets a collection with the correct groups:以下获取具有正确组的集合:

$items = OrderItem::with(['order'])
    ->get()
    ->groupBy(['fulfilment_location_id', 'product_id']);

I can then walk through this array to get the result I am looking for as follows:然后我可以遍历这个数组以获得我正在寻找的结果,如下所示:

$result = [];
foreach($items as $location_id => $products_collection){
    foreach($products_collection as $product_id => $order_items_collection){
        $sum = $order_items_collection->sum(function(OrderItem $oi){
            return $oi->qty;
        });
        isset($result[$location_id][$product_id]) ?
            $result[$location_id][$product_id] += $sum :
            $result[$location_id][$product_id] = $sum;
    }
}

... however this seems very long winded. ...然而这似乎很啰嗦。 I could get the result far easier by just duplicating the location_id column from the orders table to the order_items table, but this does not feel very nice.通过将 location_id 列从 orders 表复制到 order_items 表,我可以更容易地获得结果,但这感觉不太好。 I hoped there would be a simpler way that uses eloquent (opposed to writing a raw query).我希望有一种更简单的方式来使用 eloquent(与编写原始查询相反)。

Something along the lines of this:类似的东西:

$items = OrderItem::select(DB::raw('sum(order_items.qty) as sumqty, o.location_id as lcoation, order_items.product_id as product_id'))
            ->leftJoin('orders as o', 'o.id', 'order_items.order_id')
            ->groupBy(['product_id', 'lcoation']);

Should give you:应该给你:

sumqty | location | product_id
---------------------------------
 12       3          12                   // example data  

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM