Skip to content

Commit 058d046

Browse files
authored
LYNX-652: original_item_price must not include any discount
1 parent ea23119 commit 058d046

File tree

5 files changed

+64
-88
lines changed

5 files changed

+64
-88
lines changed

app/code/Magento/QuoteGraphQl/Model/Resolver/CartItemPrices.php

Lines changed: 48 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
<?php
22
/**
3-
* Copyright © Magento, Inc. All rights reserved.
4-
* See COPYING.txt for license details.
3+
* Copyright 2024 Adobe
4+
* All Rights Reserved.
55
*/
66
declare(strict_types=1);
77

@@ -15,6 +15,7 @@
1515
use Magento\Framework\Pricing\PriceCurrencyInterface;
1616
use Magento\Quote\Model\Cart\Totals;
1717
use Magento\Quote\Model\Quote\Item;
18+
use Magento\Downloadable\Model\Product\Type;
1819
use Magento\QuoteGraphQl\Model\Cart\TotalsCollector;
1920
use Magento\QuoteGraphQl\Model\GetDiscounts;
2021
use Magento\QuoteGraphQl\Model\GetOptionsRegularPrice;
@@ -81,15 +82,6 @@ public function resolve(Field $field, $context, ResolveInfo $info, array $value
8182
$discountAmount = $cartItem->getDiscountAmount();
8283
}
8384

84-
/**
85-
* Calculate the actual price of the product with all discounts applied
86-
*/
87-
$originalItemPrice = $cartItem->getTotalDiscountAmount() > 0
88-
? $this->priceCurrency->round(
89-
$cartItem->getCalculationPrice() - ($cartItem->getTotalDiscountAmount() / max($cartItem->getQty(), 1))
90-
)
91-
: $cartItem->getCalculationPrice();
92-
9385
return [
9486
'model' => $cartItem,
9587
'price' => [
@@ -118,7 +110,7 @@ public function resolve(Field $field, $context, ResolveInfo $info, array $value
118110
),
119111
'original_item_price' => [
120112
'currency' => $currencyCode,
121-
'value' => $originalItemPrice
113+
'value' => $this->getOriginalItemPrice($cartItem),
122114
],
123115
'original_row_total' => [
124116
'currency' => $currencyCode,
@@ -128,16 +120,34 @@ public function resolve(Field $field, $context, ResolveInfo $info, array $value
128120
}
129121

130122
/**
131-
* Calculate the original price row total
123+
* Calculate the original item price, with no discounts or taxes applied
124+
*
125+
* @param Item $cartItem
126+
* @return float
127+
*/
128+
private function getOriginalItemPrice(Item $cartItem): float
129+
{
130+
$originalItemPrice = $cartItem->getOriginalPrice() + $this->getOptionsPrice($cartItem);
131+
132+
// To add downloadable product link price to the original item price
133+
if ($cartItem->getProductType() === Type::TYPE_DOWNLOADABLE &&
134+
$cartItem->getProduct()->getData('links_purchased_separately')) {
135+
$originalItemPrice += (float)$this->getDownloadableLinkPrice($cartItem);
136+
}
137+
138+
return $originalItemPrice;
139+
}
140+
141+
/**
142+
* Calculate the original row total price
132143
*
133144
* @param Item $cartItem
134145
* @return float
135146
*/
136147
private function getOriginalRowTotal(Item $cartItem): float
137148
{
138-
$qty = $cartItem->getTotalQty();
139149
// Round unit price before multiplying to prevent losing 1 cent on subtotal
140-
return $this->priceCurrency->round($cartItem->getOriginalPrice() + $this->getOptionsPrice($cartItem)) * $qty;
150+
return $this->priceCurrency->round($this->getOriginalItemPrice($cartItem) * $cartItem->getTotalQty());
141151
}
142152

143153
/**
@@ -170,4 +180,27 @@ private function getOptionsPrice(Item $cartItem): float
170180

171181
return $price;
172182
}
183+
184+
/**
185+
* Get the downloadable link price
186+
*
187+
* @param Item $cartItem
188+
* @return float
189+
*/
190+
private function getDownloadableLinkPrice(Item $cartItem): float
191+
{
192+
$price = 0.0;
193+
$links = $cartItem->getProduct()->getCustomOption('downloadable_link_ids');
194+
if (!$links || empty($links->getValue())) {
195+
return $price;
196+
}
197+
$selectedLinks = explode(',', $links->getValue());
198+
$downloadableLinks = $cartItem->getProduct()->getTypeInstance()->getLinks($cartItem->getProduct());
199+
foreach ($downloadableLinks as $link) {
200+
if (in_array($link->getId(), $selectedLinks)) {
201+
$price += (float)$link->getPrice();
202+
}
203+
}
204+
return $price;
205+
}
173206
}

app/code/Magento/QuoteGraphQl/composer.json

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -17,7 +17,8 @@
1717
"magento/module-graph-ql": "*",
1818
"magento/module-gift-message": "*",
1919
"magento/module-catalog-inventory": "*",
20-
"magento/module-eav-graph-ql": "*"
20+
"magento/module-eav-graph-ql": "*",
21+
"magento/module-downloadable": "*"
2122
},
2223
"suggest": {
2324
"magento/module-graph-ql-cache": "*",

dev/tests/api-functional/testsuite/Magento/GraphQl/Bundle/BundleProductCartPricesTest.php

Lines changed: 8 additions & 46 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,7 @@
11
<?php
2-
/************************************************************************
3-
*
2+
/**
43
* Copyright 2024 Adobe
54
* All Rights Reserved.
6-
*
7-
* NOTICE: All information contained herein is, and remains
8-
* the property of Adobe and its suppliers, if any. The intellectual
9-
* and technical concepts contained herein are proprietary to Adobe
10-
* and its suppliers and are protected by all applicable intellectual
11-
* property laws, including trade secret and copyright laws.
12-
* Dissemination of this information or reproduction of this material
13-
* is strictly forbidden unless prior written permission is obtained
14-
* from Adobe.
15-
* ************************************************************************
165
*/
176
declare(strict_types=1);
187

@@ -113,11 +102,7 @@ public function testBundleProductFixedPriceWithOptionsWithoutPrices()
113102
$query = $this->getCartQuery($maskedQuoteId);
114103
$response = $this->graphQlQuery($query);
115104

116-
// price is the bundle product price as in this case the options don't have prices
117-
// specialPrice is the bundle product price * bundle product special price %
118-
// originalItemPriceProduct1 is the bundle product price
119-
// originalItemPriceProduct1 is with 10% discount as the special price
120-
$expectedResponse = $this->getExpectedResponse(15, 30, 30, 13.5, 27, 15, 13.5);
105+
$expectedResponse = $this->getExpectedResponse(15, 30, 30, 13.5, 27, 15, 15);
121106

122107
$this->assertEquals($expectedResponse, $response);
123108
}
@@ -185,11 +170,7 @@ public function testBundleProductFixedPriceWithOneOptionFixedPrice()
185170
$query = $this->getCartQuery($maskedQuoteId);
186171
$response = $this->graphQlQuery($query);
187172

188-
// price is the bundle product price + option fixed price
189-
// specialPrice is the bundle product price + option fixed price * bundle product special price %
190-
// originalItemPriceProduct1 is the bundle product price
191-
// originalItemPriceProduct1 is with 10% discount as the special price
192-
$expectedResponse = $this->getExpectedResponse(25, 50, 50, 22.5, 45, 25, 22.5);
173+
$expectedResponse = $this->getExpectedResponse(25, 50, 50, 22.5, 45, 25, 25);
193174

194175
$this->assertEquals($expectedResponse, $response);
195176
}
@@ -265,11 +246,7 @@ public function testBundleProductFixedPriceWithBothOptionsFixedPrice()
265246
$query = $this->getCartQuery($maskedQuoteId);
266247
$response = $this->graphQlQuery($query);
267248

268-
// price is the bundle product price + options fixed prices
269-
// specialPrice is the bundle product price + options fixed prices * bundle product special price %
270-
// originalItemPriceProduct1 is the bundle product price
271-
// originalItemPriceProduct1 is with 10% discount as the special price
272-
$expectedResponse = $this->getExpectedResponse(45, 90, 90, 40.50, 81, 45, 40.5);
249+
$expectedResponse = $this->getExpectedResponse(45, 90, 90, 40.50, 81, 45, 45);
273250

274251
$this->assertEquals($expectedResponse, $response);
275252
}
@@ -337,12 +314,7 @@ public function testBundleProductFixedPriceWithOneOptionPercentPrice()
337314
$query = $this->getCartQuery($maskedQuoteId);
338315
$response = $this->graphQlQuery($query);
339316

340-
// price is the (bundle product price * option percent price) + bundle product price
341-
// specialPrice is the (bundle product price * option percent price) +
342-
// bundle product price * bundle product special price %
343-
// originalItemPriceProduct1 is the bundle product price
344-
// originalItemPriceProduct1 is with 10% discount as the special price
345-
$expectedResponse = $this->getExpectedResponse(18, 36, 36, 16.20, 32.40, 18, 16.2);
317+
$expectedResponse = $this->getExpectedResponse(18, 36, 36, 16.20, 32.40, 18, 18);
346318

347319
$this->assertEquals($expectedResponse, $response);
348320
}
@@ -418,12 +390,7 @@ public function testBundleProductFixedPriceWithBothOptionsPercentPrices()
418390
$query = $this->getCartQuery($maskedQuoteId);
419391
$response = $this->graphQlQuery($query);
420392

421-
// price is the (bundle product price * options percent price) + bundle product price
422-
// specialPrice is the (bundle product price * options percent price) +
423-
// bundle product price * bundle product special price %
424-
// originalItemPriceProduct1 is the bundle product price
425-
// originalItemPriceProduct1 is with 10% discount as the special price
426-
$expectedResponse = $this->getExpectedResponse(19.5, 39, 39, 17.55, 35.10, 19.5, 17.55);
393+
$expectedResponse = $this->getExpectedResponse(19.5, 39, 39, 17.55, 35.10, 19.5, 19.5);
427394

428395
$this->assertEquals($expectedResponse, $response);
429396
}
@@ -499,12 +466,7 @@ public function testBundleProductFixedPriceWithOneOptionFixedAndOnePercentPrice(
499466
$query = $this->getCartQuery($maskedQuoteId);
500467
$response = $this->graphQlQuery($query);
501468

502-
// price is the (bundle product price * option percent price) + bundle product price + option fixed price
503-
// specialPrice is the (bundle product price * option percent price) + bundle product price +
504-
// option fixed price * bundle product special price %
505-
// originalItemPriceProduct1 is the bundle product price
506-
// originalItemPriceProduct1 is with 10% discount as the special price
507-
$expectedResponse = $this->getExpectedResponse(28, 56, 56, 25.20, 50.40, 28, 25.2);
469+
$expectedResponse = $this->getExpectedResponse(28, 56, 56, 25.20, 50.40, 28, 28);
508470

509471
$this->assertEquals($expectedResponse, $response);
510472
}
@@ -623,7 +585,7 @@ public function testBundleProductDynamicPriceWithSpecialPrice()
623585
"currency" => "USD"
624586
],
625587
"original_item_price" => [
626-
"value" => 25, // product 1 special_price(15) + product 2 price (10)
588+
"value" => 30, // product 1 price(20) + product 2 price (10)
627589
"currency" => "USD"
628590
]
629591
]

dev/tests/api-functional/testsuite/Magento/GraphQl/Quote/Customer/CartItemPriceTest.php

Lines changed: 1 addition & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -2,15 +2,6 @@
22
/**
33
* Copyright 2024 Adobe
44
* All Rights Reserved.
5-
*
6-
* NOTICE: All information contained herein is, and remains
7-
* the property of Adobe and its suppliers, if any. The intellectual
8-
* and technical concepts contained herein are proprietary to Adobe
9-
* and its suppliers and are protected by all applicable intellectual
10-
* property laws, including trade secret and copyright laws.
11-
* Dissemination of this information or reproduction of this material
12-
* is strictly forbidden unless prior written permission is obtained from
13-
* Adobe.
145
*/
156
declare(strict_types=1);
167

@@ -108,7 +99,7 @@ public function testGetCartItemPricesWithDiscount()
10899
0 => [
109100
'prices' => [
110101
'original_item_price' => [
111-
'value' => 8.5,
102+
'value' => 10,
112103
'currency' => 'USD'
113104
],
114105
'original_row_total' => [

dev/tests/api-functional/testsuite/Magento/GraphQl/Quote/ProductsWithCustomOptionsCartPricesTest.php

Lines changed: 5 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,18 +1,7 @@
11
<?php
2-
/************************************************************************
3-
*
2+
/**
43
* Copyright 2024 Adobe
54
* All Rights Reserved.
6-
*
7-
* NOTICE: All information contained herein is, and remains
8-
* the property of Adobe and its suppliers, if any. The intellectual
9-
* and technical concepts contained herein are proprietary to Adobe
10-
* and its suppliers and are protected by all applicable intellectual
11-
* property laws, including trade secret and copyright laws.
12-
* Dissemination of this information or reproduction of this material
13-
* is strictly forbidden unless prior written permission is obtained
14-
* from Adobe.
15-
* ************************************************************************
165
*/
176
declare(strict_types=1);
187

@@ -134,7 +123,7 @@ public function testProductsWithOneCustomOptionEnteredWithFixedPrice()
134123
"currency" => "USD"
135124
],
136125
"original_item_price" => [
137-
"value" => 25,
126+
"value" => 40,
138127
"currency" => "USD"
139128
]
140129
]
@@ -219,7 +208,7 @@ public function testProductsWithOneCustomOptionEnteredWithPercentPrice()
219208
"currency" => "USD"
220209
],
221210
"original_item_price" => [
222-
"value" => 16.5,
211+
"value" => 33,
223212
"currency" => "USD"
224213
]
225214
]
@@ -304,7 +293,7 @@ public function testProductsWithOneCustomOptionEnteredWithPercentPriceAndOneWith
304293
"currency" => "USD"
305294
],
306295
"original_item_price" => [
307-
"value" => 66.5,
296+
"value" => 83,
308297
"currency" => "USD"
309298
]
310299
]
@@ -449,7 +438,7 @@ public function testCartWithMultipleCustomProductOption()
449438
"currency" => "USD"
450439
],
451440
"original_item_price" => [
452-
"value" => 22,
441+
"value" => 46,
453442
"currency" => "USD"
454443
]
455444
]

0 commit comments

Comments
 (0)