Skip to content

Commit 6460f55

Browse files
committed
Merge branch 'MC-42811-performance' of https://github.com/magento-l3/magento2ce into L3-PR-20210830
2 parents 23d5f36 + 24aa515 commit 6460f55

File tree

3 files changed

+118
-18
lines changed

3 files changed

+118
-18
lines changed

app/code/Magento/Elasticsearch/Model/Indexer/IndexerHandler.php

Lines changed: 50 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,9 @@
55
*/
66
namespace Magento\Elasticsearch\Model\Indexer;
77

8+
use Magento\Catalog\Model\Category;
89
use Magento\CatalogSearch\Model\Indexer\Fulltext;
10+
use Magento\CatalogSearch\Model\Indexer\Fulltext\Processor;
911
use Magento\Elasticsearch\Model\Adapter\Elasticsearch as ElasticsearchAdapter;
1012
use Magento\Elasticsearch\Model\Adapter\Index\IndexNameResolver;
1113
use Magento\Framework\App\DeploymentConfig;
@@ -15,6 +17,7 @@
1517
use Magento\Framework\Indexer\SaveHandler\Batch;
1618
use Magento\Framework\Indexer\SaveHandler\IndexerInterface;
1719
use Magento\Framework\Search\Request\Dimension;
20+
use Magento\Framework\Indexer\CacheContext;
1821

1922
/**
2023
* Indexer Handler for Elasticsearch engine.
@@ -73,6 +76,16 @@ class IndexerHandler implements IndexerInterface
7376
*/
7477
private const DEPLOYMENT_CONFIG_INDEXER_BATCHES = 'indexer/batch_size/';
7578

79+
/**
80+
* @var CacheContext
81+
*/
82+
private $cacheContext;
83+
84+
/**
85+
* @var Processor
86+
*/
87+
private $processor;
88+
7689
/**
7790
* IndexerHandler constructor.
7891
* @param IndexStructureInterface $indexStructure
@@ -83,6 +96,8 @@ class IndexerHandler implements IndexerInterface
8396
* @param array $data
8497
* @param int $batchSize
8598
* @param DeploymentConfig|null $deploymentConfig
99+
* @param CacheContext|null $cacheContext
100+
* @param Processor|null $processor
86101
*/
87102
public function __construct(
88103
IndexStructureInterface $indexStructure,
@@ -91,8 +106,10 @@ public function __construct(
91106
Batch $batch,
92107
ScopeResolverInterface $scopeResolver,
93108
array $data = [],
94-
$batchSize = self::DEFAULT_BATCH_SIZE,
95-
?DeploymentConfig $deploymentConfig = null
109+
int $batchSize = self::DEFAULT_BATCH_SIZE,
110+
?DeploymentConfig $deploymentConfig = null,
111+
?CacheContext $cacheContext = null,
112+
?Processor $processor = null
96113
) {
97114
$this->indexStructure = $indexStructure;
98115
$this->adapter = $adapter;
@@ -102,6 +119,8 @@ public function __construct(
102119
$this->batchSize = $batchSize;
103120
$this->scopeResolver = $scopeResolver;
104121
$this->deploymentConfig = $deploymentConfig ?: ObjectManager::getInstance()->get(DeploymentConfig::class);
122+
$this->cacheContext = $cacheContext ?: ObjectManager::getInstance()->get(CacheContext::class);
123+
$this->processor = $processor ?: ObjectManager::getInstance()->get(Processor::class);
105124
}
106125

107126
/**
@@ -119,11 +138,40 @@ public function saveIndex($dimensions, \Traversable $documents)
119138
foreach ($this->batch->getItems($documents, $this->batchSize) as $documentsBatch) {
120139
$docs = $this->adapter->prepareDocsPerStore($documentsBatch, $scopeId);
121140
$this->adapter->addDocs($docs, $scopeId, $this->getIndexerId());
141+
if ($this->processor->getIndexer()->isScheduled()) {
142+
$this->updateCacheContext($docs);
143+
}
122144
}
123145
$this->adapter->updateAlias($scopeId, $this->getIndexerId());
124146
return $this;
125147
}
126148

149+
/**
150+
* Add category cache tags for the affected products to the cache context
151+
*
152+
* @param array $docs
153+
* @return void
154+
*/
155+
private function updateCacheContext(array $docs) : void
156+
{
157+
$categoryIds = [];
158+
foreach ($docs as $document) {
159+
if (!empty($document['category_ids'])) {
160+
if (is_array($document['category_ids'])) {
161+
foreach ($document['category_ids'] as $id) {
162+
$categoryIds[] = $id;
163+
}
164+
} elseif (is_numeric($document['category_ids'])) {
165+
$categoryIds[] = $document['category_ids'];
166+
}
167+
}
168+
}
169+
if (!empty($categoryIds)) {
170+
$categoryIds = array_unique($categoryIds);
171+
$this->cacheContext->registerEntities(Category::CACHE_TAG, $categoryIds);
172+
}
173+
}
174+
127175
/**
128176
* @inheritdoc
129177
*/

app/code/Magento/Elasticsearch/Test/Unit/Model/Indexer/IndexerHandlerTest.php

Lines changed: 63 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -7,18 +7,22 @@
77

88
namespace Magento\Elasticsearch\Test\Unit\Model\Indexer;
99

10+
use Magento\CatalogSearch\Model\Indexer\Fulltext\Processor;
1011
use Magento\AdvancedSearch\Model\Client\ClientInterface;
1112
use Magento\Elasticsearch\Model\Adapter\Elasticsearch;
1213
use Magento\Elasticsearch\Model\Adapter\Index\IndexNameResolver;
1314
use Magento\Elasticsearch\Model\Indexer\IndexerHandler;
1415
use Magento\Framework\App\ScopeInterface;
1516
use Magento\Framework\App\ScopeResolverInterface;
17+
use Magento\Framework\Indexer\IndexerInterface;
1618
use Magento\Framework\Indexer\IndexStructureInterface;
1719
use Magento\Framework\Indexer\SaveHandler\Batch;
1820
use Magento\Framework\Search\Request\Dimension;
1921
use Magento\Framework\TestFramework\Unit\Helper\ObjectManager as ObjectManagerHelper;
2022
use PHPUnit\Framework\MockObject\MockObject;
2123
use PHPUnit\Framework\TestCase;
24+
use Magento\Framework\App\DeploymentConfig;
25+
use Magento\Framework\Indexer\CacheContext;
2226

2327
/**
2428
* Test for \Magento\Elasticsearch\Model\Indexer\IndexerHandler
@@ -71,6 +75,26 @@ class IndexerHandlerTest extends TestCase
7175
*/
7276
private $scopeInterface;
7377

78+
/**
79+
* @var Processor|MockObject
80+
*/
81+
private $processor;
82+
83+
/**
84+
* @var IndexerInterface|MockObject
85+
*/
86+
private $indexer;
87+
88+
/**
89+
* @var CacheContext|MockObject
90+
*/
91+
private $cacheContext;
92+
93+
/**
94+
* @var DeploymentConfig|MockObject
95+
*/
96+
private $deploymentConfig;
97+
7498
/**
7599
* Set up test environment.
76100
*
@@ -117,26 +141,42 @@ protected function setUp(): void
117141
false
118142
);
119143

144+
$this->processor = $this->getMockBuilder(Processor::class)
145+
->disableOriginalConstructor()
146+
->getMock();
147+
$this->indexer = $this->getMockBuilder(IndexerInterface::class)
148+
->disableOriginalConstructor()
149+
->getMockForAbstractClass();
150+
$this->processor->expects($this->any())
151+
->method('getIndexer')
152+
->willReturn($this->indexer);
153+
154+
$this->deploymentConfig = $this->getMockBuilder(DeploymentConfig::class)
155+
->disableOriginalConstructor()
156+
->getMock();
157+
158+
$this->cacheContext = $this->getMockBuilder(CacheContext::class)
159+
->disableOriginalConstructor()
160+
->getMock();
161+
120162
$this->scopeInterface = $this->getMockForAbstractClass(
121163
ScopeInterface::class,
122164
[],
123165
'',
124166
false
125167
);
126168

127-
$objectManager = new ObjectManagerHelper($this);
128-
129-
$this->model = $objectManager->getObject(
130-
IndexerHandler::class,
131-
[
132-
'indexStructure' => $this->indexStructure,
133-
'adapter' => $this->adapter,
134-
'indexNameResolver' => $this->indexNameResolver,
135-
'batch' => $this->batch,
136-
'data' => ['indexer_id' => 'catalogsearch_fulltext'],
137-
500,
138-
'scopeResolver' => $this->scopeResolver
139-
]
169+
$this->model = new IndexerHandler(
170+
$this->indexStructure,
171+
$this->adapter,
172+
$this->indexNameResolver,
173+
$this->batch,
174+
$this->scopeResolver,
175+
['indexer_id' => 'catalogsearch_fulltext'],
176+
500,
177+
$this->deploymentConfig,
178+
$this->cacheContext,
179+
$this->processor
140180
);
141181
}
142182

@@ -182,7 +222,8 @@ public function testSaveIndex()
182222
{
183223
$dimensionValue = 3;
184224
$documentId = 123;
185-
$documents = new \ArrayIterator([$documentId]);
225+
$document = ['entity_id' => $documentId, 'category_ids' => [1, 2]];
226+
$documents = new \ArrayIterator([$document]);
186227

187228
$dimension = $this->getMockBuilder(Dimension::class)
188229
->disableOriginalConstructor()
@@ -199,17 +240,23 @@ public function testSaveIndex()
199240
$this->adapter->expects($this->once())
200241
->method('prepareDocsPerStore')
201242
->with([], $dimensionValue)
202-
->willReturn([$documentId]);
243+
->willReturn([$document]);
203244
$this->adapter->expects($this->once())
204245
->method('addDocs')
205-
->with([$documentId]);
246+
->with([$document]);
206247
$this->scopeResolver->expects($this->once())
207248
->method('getScope')
208249
->willReturn($this->scopeInterface);
209250
$this->scopeInterface->expects($this->once())
210251
->method('getId')
211252
->willReturn($dimensionValue);
212253

254+
$this->indexer->expects($this->once())
255+
->method('isScheduled')
256+
->willReturn(true);
257+
$this->cacheContext->expects($this->once())
258+
->method('registerEntities');
259+
213260
$result = $this->model->saveIndex([$dimension], $documents);
214261

215262
$this->assertEquals($this->model, $result);

app/code/Magento/Elasticsearch/etc/di.xml

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -564,4 +564,9 @@
564564
<type name="Magento\Catalog\Model\ResourceModel\Attribute">
565565
<plugin name="updateElasticsearchIndexerMapping" type="Magento\Elasticsearch\Model\Indexer\Fulltext\Plugin\Category\Product\Attribute"/>
566566
</type>
567+
<type name="Magento\Elasticsearch\Model\Indexer\IndexerHandler">
568+
<arguments>
569+
<argument name="cacheContext" xsi:type="object">Magento\Framework\Indexer\CacheContext\Proxy</argument>
570+
</arguments>
571+
</type>
567572
</config>

0 commit comments

Comments
 (0)