Laravel Eloquent Sum ของคอลัมน์ความสัมพันธ์


112

ฉันทำงานเกี่ยวกับแอปพลิเคชัน shoppingcart และตอนนี้ฉันพบปัญหาต่อไปนี้ ..

มีผู้ใช้ผลิตภัณฑ์และวัตถุในรถเข็น
- ตารางรถเข็นมีเฉพาะคอลัมน์ต่อไปนี้: "id", "user_id", "product_id" และการประทับเวลา
- UserModel "hasMany" Carts (เนื่องจากผู้ใช้สามารถจัดเก็บสินค้าได้หลายรายการ)
- CartModel "เป็นของถึง" ผู้ใช้และ CartModel "hasMany" ผลิตภัณฑ์

ตอนนี้ในการคำนวณผลิตภัณฑ์ทั้งหมดฉันสามารถโทร: Auth::user()->cart()->count().

คำถามของฉันคือฉันจะรับ SUM () ของราคา (คอลัมน์ของผลิตภัณฑ์) ของสินค้าในรถเข็นโดยผู้ใช้รายนี้ได้อย่างไร?
ฉันต้องการทำสิ่งนี้ให้สำเร็จด้วย Eloquent ไม่ใช่โดยใช้แบบสอบถาม (ส่วนใหญ่ฉันเชื่อว่ามันสะอาดกว่ามาก)

คำตอบ:


220
Auth::user()->products->sum('price');

เอกสารเป็นไฟเล็ก ๆ น้อย ๆ สำหรับบางส่วนของCollectionวิธีการ แต่ทั้งหมดมวลสร้างแบบสอบถามดูเหมือนจะพร้อมใช้งานนอกเหนือจากการavg()ที่สามารถพบได้ที่http://laravel.com/docs/queries#aggregates


ว้าวขอบคุณสำหรับการตอบกลับอย่างรวดเร็ว ตอนนี้บอกว่าไม่มีคอลัมน์ราคา ดูเหมือน
ฝีไม้ลายมือ

3
ที่จริงแล้วคุณต้องเพิ่มตารางผลิตภัณฑ์ลงในความสัมพันธ์ขอโทษ ลอง$sum = Auth::user()->cart()->products()->sum('price');หรืออะไรก็ตามที่คอลัมน์ราคาอยู่ในตารางผลิตภัณฑ์ของคุณ
user1669496

1
ที่ได้ผลสำหรับฉัน! ฉันเลิกใช้ cartclasses แล้ว ตอนนี้ทั้งผู้ใช้และผลิตภัณฑ์มีเมธอด belongToMany () ตอนนี้ฉันสามารถใช้ price: {{Auth :: user () -> products-> sum ('price')}} Thanx กรณีนี้ได้รับการแก้ไขแล้ว
พลเรือเอก

10
มีบางอย่างไม่ถูกต้องที่นี่ - ลิงก์ของคุณหมายถึงการใช้ฟังก์ชันรวมกับการสืบค้นฐานข้อมูล แต่products->sumหมายความว่าเป็นการเรียกรวมบนวัตถุคอลเลกชันแทนที่จะเป็นวัตถุตัวสร้างที่ส่งคืนโดยผลิตภัณฑ์ () มันคุ้มค่าที่จะชี้แจงว่าคุณหมายถึงอะไรที่นี่และให้ลิงค์เพื่ออธิบายทั้งสองอย่าง
Benubird

1
@ user3253002 โดยใช้ความสัมพันธ์โดยไม่มีวงเล็บ...->products->...จะสอบถามฐานข้อมูลเพื่อรับผลิตภัณฑ์ที่เกี่ยวข้องของโมเดลปัจจุบันทั้งหมดจากนั้นทำงานกับคอลเล็กชันในหน่วยความจำนั้น การใช้...->products()->...เพียงแค่ปรับเปลี่ยนแบบสอบถามที่กำลังสร้างโดยไม่ต้องดำเนินการจนกว่าจะมีการเรียกสิ่งที่ต้องการ->sum()หลังนี้มีประสิทธิภาพมากขึ้นเนื่องจากหลีกเลี่ยงการถ่ายโอนข้อมูลที่ไม่จำเป็นจากฐานข้อมูลไปยังหน่วยความจำ
Siegen

62

นี่ไม่ใช่คำตอบของคุณ แต่สำหรับผู้ที่มาที่นี่เพื่อค้นหาวิธีแก้ปัญหาอื่น ฉันต้องการรับผลรวมของคอลัมน์ของตารางที่เกี่ยวข้องตามเงื่อนไข ในดีลฐานข้อมูลของฉันมีกิจกรรมมากมายฉันต้องการรับผลรวมของ "amount_total" จากตารางกิจกรรมโดยที่ activity.deal_id = deal.id และ activities.status = จ่ายดังนั้นฉันจึงทำเช่นนี้

$query->withCount([
'activity AS paid_sum' => function ($query) {
            $query->select(DB::raw("SUM(amount_total) as paidsum"))->where('status', 'paid');
        }
    ]);

มันกลับมา

"paid_sum_count" => "320.00"

ในแอตทริบิวต์ดีล

ตอนนี้มันคือผลรวมที่ฉันต้องการไม่นับ


4
นี่เป็นวิธีที่ดีที่สุดในหลาย ๆ กรณีเพราะคุณสามารถจัดเรียงโดยไม่ต้องรับบันทึกทั้งหมด
Sabrina Leggett

15

ฉันลองทำสิ่งที่คล้ายกันซึ่งต้องใช้เวลานานพอสมควรก่อนที่ฉันจะหาฟังก์ชัน collect () ได้ ดังนั้นคุณสามารถมีบางอย่างในลักษณะนี้:

collect($items)->sum('amount');

สิ่งนี้จะทำให้คุณได้ผลรวมของรายการทั้งหมด


4
ชื่อของฟังก์ชั่นคือcollect()
Leonardo Beal

คุณอาจจะดีกว่าแค่วนลูปอาร์เรย์ collect()ใช้เพื่อเพิ่มอาร์เรย์ให้เป็นวัตถุคอลเลกชัน แต่ถ้าคุณไม่มีคอลเล็กชันตั้งแต่แรกอาจเป็นการดีกว่าที่จะใช้อาร์เรย์ดิบ
Flame

0

ยังใช้ตัวสร้างแบบสอบถาม

DB::table("rates")->get()->sum("rate_value")

เพื่อให้ได้ผลรวมของมูลค่าอัตราทั้งหมดภายในอัตราตาราง

เพื่อรับผลรวมของผลิตภัณฑ์ของผู้ใช้

DB::table("users")->get()->sum("products")
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.