Reputation: 1055
I have a table with sales details.
Buyer can buy several items and pay all together: in this case, OrderID
is the same for all items and the PaymentAmount
and PaymentID
too
But it can happen that they pay in 2 installments, in this case there are different PaymentID
(while payment amount can be the same).
I need to check that shipping costs are correctly calculated, from difference between PaymentAmounts
and Quantity*Price
Relevant columns are:
| SaleID | OrderID | Quantity | Price | PaymentAmount | PaymentID | Shippingcost |
| 0001 | 001 | 3 | 3.50 | 13.50 | BT123 | 3.00 |
| 0002 | 002 | 1 | 1.50 | 13.50 | BB331 | 5.50 |
| 0003 | 002 | 5 | 2.00 | 13.50 | BB331 | 5.50 |
| 0004 | 002 | 2 | 5.00 | 13.50 | BB332 | 5.50 |
| 0005 | 003 | 1 | 3.00 | 12.50 | BV444 | 4.00 |
| 0006 | 003 | 1 | 5.50 | 12.50 | BV444 | 4.00 |
therefore for the same
OrderID
I need to sum the payment amounts that have different PaymentID
, and I have to sum all quantity and prices:
Therefore for OrderID 002 I would expect:
TotalPayments 27.00
TotalGoods 21.50
ShippingCosts 5.50
So far my solution looks like this:
declare @OrderID nvarchar(10)='0002'
select distinct
paymentAmount,
sum (quantitypurchased*currentprice) over (partition by OID) TotalGoods
from
Sales s
where
OrderID = @OrderID
and
declare @OrderID nvarchar(10) = '0002'
select distinct
sum(paymentAmount) over () TotalPayments,
sum (quantitypurchased * currentprice) over (partition by OID) TotalGoods
from
Sales s
where
OrderID = @OrderID
The problem is that the first solution does not return the totals, although have the right figures to calculate it.
But main issue is that returns more than 1 row, while for further processing I would need to have the total goods and total payments in a single row
While the second returns the totals in one row, but TotalPayments is wrong since value are added more than 1 time.
And I'm quite sure this can be "easily" achieved with a little more skills..
Can help a little?
Upvotes: 0
Views: 37
Reputation: 883
I came up with the same logic as Gordon's answer but instead, I used CTE.
;With CTE
As
(
Select
OrderID,
Quantity,
Price,
PaymentAmount,
ShippingCost,
ROW_NUMBER() Over(Partition By OrderID, PaymentID Order By OrderID) As RowNum
From Sales
)
Select
OrderID,
Sum(Case When RowNum = 1 Then PaymentAmount End) As TotalPayments,
Sum(Quantity * Price) As TotalCosts,
Max(ShippingCost) As ShippingCost
From CTE
Group By OrderID
Order By OrderID;
Upvotes: 0
Reputation: 1269773
I think window functions can help you isolate the rows that need to be involved in the calculations:
select s.orderid,
sum(case when seqnum = 1 then paymentamount else 0 end) as totalpayments,
sum(quantity * price) as totalprice,
max(shippingcost) as shippingcost
from (select s.*,
row_number() over (partition by s.orderid, s.paymentid order by saleid) as seqnum
from sales s
) s
group by s.orderid;
Upvotes: 1