Skip to content

Commit fdf18ee

Browse files
committed
Merge branch 'fix-order-spam-when-search-is-down' of github.com:texboy/magento2 into 2.4-develop-prs
2 parents f04a94a + 9b0ec3c commit fdf18ee

File tree

2 files changed

+252
-36
lines changed

2 files changed

+252
-36
lines changed

app/code/Magento/CatalogInventory/Observer/ReindexQuoteInventoryObserver.php

Lines changed: 59 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -4,41 +4,58 @@
44
* See COPYING.txt for license details.
55
*/
66

7+
declare(strict_types=1);
8+
79
namespace Magento\CatalogInventory\Observer;
810

11+
use Magento\CatalogInventory\Model\Indexer\Stock\Processor as StockProcessor;
12+
use Magento\Catalog\Model\Indexer\Product\Price\Processor as PriceProcessor;
913
use Magento\Framework\Event\Observer as EventObserver;
1014
use Magento\Framework\Event\ObserverInterface;
15+
use Magento\Framework\Exception\LocalizedException;
16+
use Psr\Log\LoggerInterface;
1117

18+
/**
19+
* Responsible for re-indexing stock items after a successful order.
20+
*/
1221
class ReindexQuoteInventoryObserver implements ObserverInterface
1322
{
1423
/**
15-
* @var \Magento\CatalogInventory\Model\Indexer\Stock\Processor
24+
* @var StockProcessor
1625
*/
17-
protected $stockIndexerProcessor;
26+
private StockProcessor $stockIndexerProcessor;
1827

1928
/**
20-
* @var \Magento\Catalog\Model\Indexer\Product\Price\Processor
29+
* @var PriceProcessor
2130
*/
22-
protected $priceIndexer;
31+
private PriceProcessor $priceIndexer;
2332

2433
/**
25-
* @var \Magento\CatalogInventory\Observer\ItemsForReindex
34+
* @var ItemsForReindex
2635
*/
27-
protected $itemsForReindex;
36+
private ItemsForReindex $itemsForReindex;
2837

2938
/**
30-
* @param \Magento\CatalogInventory\Model\Indexer\Stock\Processor $stockIndexerProcessor
31-
* @param \Magento\Catalog\Model\Indexer\Product\Price\Processor $priceIndexer
39+
* @var LoggerInterface
40+
*/
41+
private LoggerInterface $logger;
42+
43+
/**
44+
* @param StockProcessor $stockIndexerProcessor
45+
* @param PriceProcessor $priceIndexer
3246
* @param ItemsForReindex $itemsForReindex
47+
* @param LoggerInterface $logger
3348
*/
3449
public function __construct(
35-
\Magento\CatalogInventory\Model\Indexer\Stock\Processor $stockIndexerProcessor,
36-
\Magento\Catalog\Model\Indexer\Product\Price\Processor $priceIndexer,
37-
ItemsForReindex $itemsForReindex
50+
StockProcessor $stockIndexerProcessor,
51+
PriceProcessor $priceIndexer,
52+
ItemsForReindex $itemsForReindex,
53+
LoggerInterface $logger
3854
) {
3955
$this->stockIndexerProcessor = $stockIndexerProcessor;
4056
$this->priceIndexer = $priceIndexer;
4157
$this->itemsForReindex = $itemsForReindex;
58+
$this->logger = $logger;
4259
}
4360

4461
/**
@@ -47,37 +64,43 @@ public function __construct(
4764
* @param EventObserver $observer
4865
* @return void
4966
*/
50-
public function execute(EventObserver $observer)
67+
public function execute(EventObserver $observer): void
5168
{
52-
// Reindex quote ids
53-
$quote = $observer->getEvent()->getQuote();
54-
$productIds = [];
55-
foreach ($quote->getAllItems() as $item) {
56-
$productIds[$item->getProductId()] = $item->getProductId();
57-
$children = $item->getChildrenItems();
58-
if ($children) {
59-
foreach ($children as $childItem) {
60-
$productIds[$childItem->getProductId()] = $childItem->getProductId();
69+
try {
70+
// Reindex quote ids
71+
$quote = $observer->getEvent()->getData('quote');
72+
$productIds = [];
73+
foreach ($quote->getAllItems() as $item) {
74+
$productIds[$item->getData('product_id')] = $item->getData('product_id');
75+
$children = $item->getData('children_items');
76+
if ($children) {
77+
foreach ($children as $childItem) {
78+
$productIds[$childItem->getData('product_id')] = $childItem->getData('product_id');
79+
}
6180
}
6281
}
63-
}
6482

65-
if ($productIds) {
66-
$this->stockIndexerProcessor->reindexList($productIds);
67-
}
83+
if ($productIds) {
84+
$this->stockIndexerProcessor->reindexList($productIds);
85+
}
6886

69-
// Reindex previously remembered items
70-
$productIds = [];
71-
foreach ($this->itemsForReindex->getItems() as $item) {
72-
$item->save();
73-
$productIds[] = $item->getProductId();
74-
}
87+
// Reindex previously remembered items
88+
$productIds = [];
89+
foreach ($this->itemsForReindex->getItems() as $item) {
90+
$item->save();
91+
$productIds[] = $item->getData('product_id');
92+
}
7593

76-
if (!empty($productIds)) {
77-
$this->priceIndexer->reindexList($productIds);
78-
}
94+
if (!empty($productIds)) {
95+
$this->priceIndexer->reindexList($productIds);
96+
}
7997

80-
$this->itemsForReindex->clear();
81-
// Clear list of remembered items - we don't need it anymore
98+
$this->itemsForReindex->clear();
99+
// Clear list of remembered items - we don't need it anymore
100+
} catch (LocalizedException $exception) {
101+
$this->logger->error('Error while re-indexing order items: ' . $exception->getLogMessage());
102+
$this->stockIndexerProcessor->markIndexerAsInvalid();
103+
$this->priceIndexer->markIndexerAsInvalid();
104+
}
82105
}
83106
}
Lines changed: 193 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,193 @@
1+
<?php
2+
/**
3+
* Copyright © Magento, Inc. All rights reserved.
4+
* See COPYING.txt for license details.
5+
*/
6+
7+
declare(strict_types=1);
8+
9+
namespace Magento\CatalogInventory\Test\Unit\Observer;
10+
11+
use Magento\Catalog\Model\Indexer\Product\Price\Processor as PriceProcessor;
12+
use Magento\CatalogInventory\Model\Indexer\Stock\Processor as StockProcessor;
13+
use Magento\CatalogInventory\Observer\ItemsForReindex;
14+
use Magento\CatalogInventory\Observer\ReindexQuoteInventoryObserver;
15+
use Magento\Framework\Event;
16+
use Magento\Framework\Event\Observer;
17+
use Magento\Framework\Exception\LocalizedException;
18+
use Magento\Quote\Model\Quote;
19+
use Magento\Quote\Model\Quote\Item;
20+
use PHPUnit\Framework\TestCase;
21+
use Psr\Log\LoggerInterface;
22+
23+
/**
24+
* Test class for ReindexQuoteInventoryObserver
25+
*/
26+
class ReindexQuoteInventoryObserverTest extends TestCase
27+
{
28+
/**
29+
* @var StockProcessor
30+
*/
31+
private StockProcessor $stockIndexerProcessor;
32+
33+
/**
34+
* @var PriceProcessor
35+
*/
36+
private PriceProcessor $priceIndexer;
37+
38+
/**
39+
* @var ItemsForReindex
40+
*/
41+
private ItemsForReindex $itemsForReindex;
42+
43+
/**
44+
* @var LoggerInterface
45+
*/
46+
private LoggerInterface $logger;
47+
48+
/**
49+
* @var Observer
50+
*/
51+
private Observer $observedObject;
52+
53+
/**
54+
* @var Event
55+
*/
56+
private Event $event;
57+
58+
/**
59+
* @var Quote
60+
*/
61+
private Quote $quote;
62+
63+
/**
64+
* @var Item
65+
*/
66+
private Item $quoteItem;
67+
68+
/**
69+
* @var ReindexQuoteInventoryObserver
70+
*/
71+
private ReindexQuoteInventoryObserver $sut;
72+
73+
/**
74+
* @inheritDoc
75+
*/
76+
public function setUp(): void
77+
{
78+
$this->stockIndexerProcessor = $this->createMock(StockProcessor::class);
79+
$this->priceIndexer = $this->createMock(PriceProcessor::class);
80+
$this->itemsForReindex = $this->createMock(ItemsForReindex::class);
81+
$this->logger = $this->createMock(LoggerInterface::class);
82+
$this->observedObject = $this->createMock(Observer::class);
83+
$this->event = $this->createMock(Event::class);
84+
$this->quote = $this->createMock(Quote::class);
85+
$this->quoteItem = $this->createMock(Item::class);
86+
87+
$this->sut = new ReindexQuoteInventoryObserver(
88+
$this->stockIndexerProcessor,
89+
$this->priceIndexer,
90+
$this->itemsForReindex,
91+
$this->logger
92+
);
93+
}
94+
95+
/**
96+
* Test execute should re-index quote stock items.
97+
*
98+
* @test
99+
*
100+
* @return void
101+
*/
102+
public function execute(): void
103+
{
104+
$this->observedObject->expects($this->once())
105+
->method('getEvent')
106+
->willReturn($this->event);
107+
108+
$this->event->expects($this->once())
109+
->method('getData')
110+
->with('quote')
111+
->willReturn($this->quote);
112+
113+
$this->quote->expects($this->once())
114+
->method('getAllItems')
115+
->willReturn([$this->quoteItem]);
116+
117+
$this->quoteItem->expects($this->exactly(6))
118+
->method('getData')
119+
->withConsecutive(
120+
['product_id'],
121+
['product_id'],
122+
['children_items'],
123+
['product_id'],
124+
['product_id'],
125+
['product_id']
126+
)->willReturnOnConsecutiveCalls(1, 1, [$this->quoteItem], 1, 1, 1);
127+
128+
$this->stockIndexerProcessor->expects($this->once())
129+
->method('reindexList')
130+
->with([1 => 1]);
131+
132+
$this->itemsForReindex->expects($this->once())
133+
->method('getItems')
134+
->willReturn([$this->quoteItem]);
135+
136+
$this->priceIndexer->expects($this->once())
137+
->method('reindexList')
138+
->with([1]);
139+
140+
$this->itemsForReindex->expects($this->once())
141+
->method('clear');
142+
143+
$this->sut->execute($this->observedObject);
144+
}
145+
146+
/**
147+
* Test execute should log error on exception.
148+
*
149+
* @test
150+
*
151+
* @return void
152+
*/
153+
public function executeShouldLogOnException(): void
154+
{
155+
$this->observedObject->expects($this->once())
156+
->method('getEvent')
157+
->willReturn($this->event);
158+
159+
$this->event->expects($this->once())
160+
->method('getData')
161+
->with('quote')
162+
->willReturn($this->quote);
163+
164+
$this->quote->expects($this->once())
165+
->method('getAllItems')
166+
->willReturn([$this->quoteItem]);
167+
168+
$this->quoteItem->expects($this->exactly(3))
169+
->method('getData')
170+
->withConsecutive(
171+
['product_id'],
172+
['product_id'],
173+
['children_items']
174+
)->willReturnOnConsecutiveCalls(1, 1, []);
175+
176+
$this->stockIndexerProcessor->expects($this->once())
177+
->method('reindexList')
178+
->with([1 => 1])
179+
->willThrowException(new LocalizedException(__('error')));
180+
181+
$this->logger->expects($this->once())
182+
->method('error')
183+
->with('Error while re-indexing order items: error');
184+
185+
$this->stockIndexerProcessor->expects($this->once())
186+
->method('markIndexerAsInvalid');
187+
188+
$this->priceIndexer->expects($this->once())
189+
->method('markIndexerAsInvalid');
190+
191+
$this->sut->execute($this->observedObject);
192+
}
193+
}

0 commit comments

Comments
 (0)