Skip to content

Commit ab42ff6

Browse files
committed
MC-38038: Partial reindex of prices causes empty categories (missed products)
1 parent 84339f8 commit ab42ff6

File tree

2 files changed

+156
-6
lines changed
  • app/code/Magento/Catalog

2 files changed

+156
-6
lines changed

app/code/Magento/Catalog/Model/Indexer/Product/Price/Action/Rows.php

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,7 +13,6 @@
1313
use Magento\Catalog\Model\ResourceModel\Product\Indexer\Price\Factory;
1414
use Magento\Catalog\Model\ResourceModel\Product\Indexer\Price\TierPrice;
1515
use Magento\Framework\App\Config\ScopeConfigInterface;
16-
use Magento\Framework\App\ObjectManager;
1716
use Magento\Framework\Stdlib\DateTime;
1817
use Magento\Framework\Stdlib\DateTime\TimezoneInterface;
1918
use Magento\Store\Model\StoreManagerInterface;

app/code/Magento/Catalog/Test/Unit/Model/Indexer/Product/Price/Action/RowsTest.php

Lines changed: 156 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -7,27 +7,178 @@
77

88
namespace Magento\Catalog\Test\Unit\Model\Indexer\Product\Price\Action;
99

10+
use Magento\Store\Model\StoreManagerInterface;
11+
use Magento\Directory\Model\CurrencyFactory;
12+
use Magento\Catalog\Model\Product\Type;
13+
use Magento\Catalog\Model\ResourceModel\Product\Indexer\Price\Factory;
14+
use Magento\Catalog\Model\ResourceModel\Product\Indexer\Price\DefaultPrice;
15+
use Magento\Catalog\Model\ResourceModel\Product\Indexer\Price\TierPrice;
16+
use Magento\Catalog\Model\Indexer\Product\Price\DimensionCollectionFactory;
17+
use Magento\Catalog\Model\Indexer\Product\Price\TableMaintainer;
1018
use Magento\Catalog\Model\Indexer\Product\Price\Action\Rows;
11-
use Magento\Framework\TestFramework\Unit\Helper\ObjectManager;
19+
use Magento\Framework\App\Config\ScopeConfigInterface;
20+
use Magento\Framework\Stdlib\DateTime;
21+
use Magento\Framework\Stdlib\DateTime\TimezoneInterface;
22+
use Magento\Framework\DB\Adapter\AdapterInterface;
23+
use Magento\Framework\DB\Select;
24+
use Magento\Framework\Indexer\MultiDimensionProvider;
1225
use PHPUnit\Framework\TestCase;
26+
use PHPUnit\Framework\MockObject\MockObject;
1327

1428
class RowsTest extends TestCase
1529
{
1630
/**
1731
* @var Rows
1832
*/
19-
protected $_model;
33+
private $actionRows;
34+
35+
/**
36+
* @var ScopeConfigInterface|MockObject
37+
*/
38+
private $config;
39+
40+
/**
41+
* @var StoreManagerInterface|MockObject
42+
*/
43+
private $storeManager;
44+
45+
/**
46+
* @var CurrencyFactory|MockObject
47+
*/
48+
private $currencyFactory;
49+
50+
/**
51+
* @var TimezoneInterface|MockObject
52+
*/
53+
private $localeDate;
54+
55+
/**
56+
* @var DateTime|MockObject
57+
*/
58+
private $dateTime;
59+
60+
/**
61+
* @var Type|MockObject
62+
*/
63+
private $catalogProductType;
64+
65+
/**
66+
* @var Factory|MockObject
67+
*/
68+
private $indexerPriceFactory;
69+
70+
/**
71+
* @var DefaultPrice|MockObject
72+
*/
73+
private $defaultIndexerResource;
74+
75+
/**
76+
* @var TierPrice|MockObject
77+
*/
78+
private $tierPriceIndexResource;
79+
80+
/**
81+
* @var DimensionCollectionFactory|MockObject
82+
*/
83+
private $dimensionCollectionFactory;
84+
85+
/**
86+
* @var TableMaintainer|MockObject
87+
*/
88+
private $tableMaintainer;
2089

2190
protected function setUp(): void
2291
{
23-
$objectManager = new ObjectManager($this);
24-
$this->_model = $objectManager->getObject(Rows::class);
92+
$this->config = $this->getMockBuilder(ScopeConfigInterface::class)
93+
->getMockForAbstractClass();
94+
$this->storeManager = $this->getMockBuilder(StoreManagerInterface::class)
95+
->getMockForAbstractClass();
96+
$this->currencyFactory = $this->getMockBuilder(CurrencyFactory::class)
97+
->disableOriginalConstructor()
98+
->getMock();
99+
$this->localeDate = $this->getMockBuilder(TimezoneInterface::class)
100+
->getMockForAbstractClass();
101+
$this->dateTime = $this->getMockBuilder(DateTime::class)
102+
->disableOriginalConstructor()
103+
->getMock();
104+
$this->catalogProductType = $this->getMockBuilder(Type::class)
105+
->disableOriginalConstructor()
106+
->getMock();
107+
$this->indexerPriceFactory = $this->getMockBuilder(Factory::class)
108+
->disableOriginalConstructor()
109+
->getMock();
110+
$this->defaultIndexerResource = $this->getMockBuilder(DefaultPrice::class)
111+
->disableOriginalConstructor()
112+
->getMock();
113+
$this->tierPriceIndexResource = $this->getMockBuilder(TierPrice::class)
114+
->disableOriginalConstructor()
115+
->getMock();
116+
$this->dimensionCollectionFactory = $this->getMockBuilder(DimensionCollectionFactory::class)
117+
->disableOriginalConstructor()
118+
->getMock();
119+
$this->tableMaintainer = $this->getMockBuilder(TableMaintainer::class)
120+
->disableOriginalConstructor()
121+
->getMock();
122+
$batchSize = 2;
123+
124+
$this->actionRows = new Rows(
125+
$this->config,
126+
$this->storeManager,
127+
$this->currencyFactory,
128+
$this->localeDate,
129+
$this->dateTime,
130+
$this->catalogProductType,
131+
$this->indexerPriceFactory,
132+
$this->defaultIndexerResource,
133+
$this->tierPriceIndexResource,
134+
$this->dimensionCollectionFactory,
135+
$this->tableMaintainer,
136+
$batchSize
137+
);
25138
}
26139

27140
public function testEmptyIds()
28141
{
29142
$this->expectException('Magento\Framework\Exception\InputException');
30143
$this->expectExceptionMessage('Bad value was supplied.');
31-
$this->_model->execute(null);
144+
$this->actionRows->execute(null);
145+
}
146+
147+
public function testBatchProcessing()
148+
{
149+
$ids = [1, 2, 3, 4];
150+
$select = $this->getMockBuilder(Select::class)
151+
->disableOriginalConstructor()
152+
->getMock();
153+
$select->expects($this->any())->method('from')->willReturnSelf();
154+
$select->expects($this->any())->method('where')->willReturnSelf();
155+
$select->expects($this->any())->method('join')->willReturnSelf();
156+
$adapter = $this->getMockBuilder(AdapterInterface::class)->getMockForAbstractClass();
157+
$adapter->expects($this->any())->method('select')->willReturn($select);
158+
$this->defaultIndexerResource->expects($this->any())
159+
->method('getConnection')
160+
->willReturn($adapter);
161+
$adapter->expects($this->any())
162+
->method('fetchAll')
163+
->with($select)
164+
->willReturn([]);
165+
$adapter->expects($this->any())
166+
->method('fetchPairs')
167+
->with($select)
168+
->willReturn([]);
169+
$multiDimensionProvider = $this->getMockBuilder(MultiDimensionProvider::class)
170+
->disableOriginalConstructor()
171+
->getMock();
172+
$this->dimensionCollectionFactory->expects($this->exactly(2))
173+
->method('create')
174+
->willReturn($multiDimensionProvider);
175+
$iterator = new \ArrayObject([]);
176+
$multiDimensionProvider->expects($this->exactly(2))
177+
->method('getIterator')
178+
->willReturn($iterator);
179+
$this->catalogProductType->expects($this->any())
180+
->method('getTypesByPriority')
181+
->willReturn([]);
182+
$this->actionRows->execute($ids);
32183
}
33184
}

0 commit comments

Comments
 (0)