【发布时间】:2021-09-09 13:24:14
【问题描述】:
我想就使用查询构建器从关联模型中获取多个总和的方法寻求建议。
一共有三个表:
invoices invoice_items payment_receipts
-------- ------------- -------------
id | name id| invoice_id | invoice_qty unit_price id| invoice_id | receipt_amount
===|====== ========================================== ================================
1 |INV01 1| 1 | 1300 |12.00 1 | 1 | 1000
2 |INV02 2| 1 | 2600 |9.00 2 | 1 | 2000
3 |INV03 3| 2 | 1100 |15.00 3 | 3 | 900
4| 3 | 900 |12:00
对于每张发票,我想要商品总金额的总和(数量 * 价格),以及付款收据的总和。
这个查询(带有子查询)正确地得到了我正在寻找的结果:
SELECT Invoices.id, Invoices.invoice_name, InvoiceItemSum.SumOfAmount, PaymentSum.SumOfPaymentAmount
FROM Invoices
INNER JOIN (
SELECT invoice_id, SUM(Invoice_items.invoice_qty * Invoice_items.unit_price) AS SumOfAmount
FROM Invoice_items
GROUP BY Invoice_id
) InvoiceItemSum ON InvoiceItemSum.Invoice_id = Invoices.id
LEFT JOIN (
SELECT Invoice_id, SUM(Payment_receipts.receipt_amount) AS SumOfPaymentAmount
FROM Payment_receipts
GROUP BY Invoice_id
) PaymentSum ON PaymentSum.Invoice_id = Invoices.id
WHERE Invoices.invoice_id = 33
我可以直接在我的 CakePhp 应用程序中执行这个查询并获得我需要的结果,所以它就是这样工作的。
不过,我想通过查询构建器获得关于更优雅的 CakePHP 方法的建议。
我试过这个:
$query = $this->Invoices->find()->contain(['InvoiceItems', 'PaymentReceipts']);
$query->select([
'Invoices.id',
'Invoices.invoice_name',
]);
$query->select([
'total_inv_amt' => $query->func()->sum('InvoiceItems.invoice_qty * InvoiceItems.unit_price'),
'total_paid_amt' => $query->func()->sum('PaymentReceipts.receipt_amount')
])
->innerJoinWith('InvoiceItems')
->leftJoinWith('PaymentReceipts')
->group(['Invoices.id']);
$query->where(['Invoices.id' => 33]);
但这会导致通过创建此查询将两个总和加倍:
SELECT
Invoices.id AS Invoices__id,
Invoices.invoice_name AS Invoices__invoice_name,
(
SUM(
InvoiceItems.invoice_qty * InvoiceItems.unit_price
)
) AS total_inv_amt,
(
SUM(PaymentReceipts.receipt_amount)
) AS total_paid_amt
FROM
invoices Invoices
INNER JOIN invoice_items InvoiceItems ON Invoices.id = (InvoiceItems.invoice_id)
LEFT JOIN payment_receipts PaymentReceipts ON Invoices.id = (PaymentReceipts.invoice_id)
WHERE
Invoices.id = 33
GROUP BY
Invoices.id
我在文档之后尝试了子查询,但结果无数。我也玩过连接,但仍然没有骰子。
我的问题是:使用查询生成器编写此查询的好方法是什么?
提前感谢您的任何建议!
【问题讨论】:
-
你是不是总结错了?
-
没错……总和翻了一番。
-
让我更正一下。如果只有一个发票项目,则结果是正确的。如果有多个发票项目,则总发票金额为 SUM * 2,总付款金额为 SUM * 发票项目数。
-
请注意,单独运行 InvoiceItems SUM 或 PaymentReceipts SUM 都可以正常工作。当我们将两个连接查询放在一起时,它会乘以总数。
标签: cakephp cakephp-4.x