Skip to content

Commit 8931b9c

Browse files
authored
Merge pull request #425 from magento-south/BUGS
[South] Bugfixes - MAGETWO-58277 Saving category on catalog with 20k+ products is very slow (from 5mins till 1 hour) - MAGETWO-23764 Category/Product Indexer fails with mysql fatal on large catalog - MAGETWO-33568 Customer is redirected to "Compare Products" Frontend page if tries to remove a Product from comparing - MAGETWO-56512 Products created via REST API are not visible after enabling the product via scope = All Store Views - MAGETWO-55154 [GitHub] IndexerHandlerFactory: Indexer Object cast to String - MAGETWO-57835 [Github] Cannot save customer dob attribute if admin interface locale is en_GB #6323 - MAGETWO-57629 ACL not used on grid quick edits
2 parents c5d04c6 + c37e8ce commit 8931b9c

File tree

31 files changed

+1414
-282
lines changed

31 files changed

+1414
-282
lines changed

app/code/Magento/Catalog/Controller/Adminhtml/Category.php

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ abstract class Category extends \Magento\Backend\App\Action
3131
*/
3232
protected function _initCategory($getRootInstead = false)
3333
{
34-
$categoryId = (int)$this->getRequest()->getParam('id', false);
34+
$categoryId = $this->resolveCategoryId();
3535
$storeId = (int)$this->getRequest()->getParam('store');
3636
$category = $this->_objectManager->create(\Magento\Catalog\Model\Category::class);
3737
$category->setStoreId($storeId);
@@ -62,6 +62,18 @@ protected function _initCategory($getRootInstead = false)
6262
return $category;
6363
}
6464

65+
/**
66+
* Resolve Category Id (from get or from post)
67+
*
68+
* @return int
69+
*/
70+
private function resolveCategoryId()
71+
{
72+
$categoryId = (int)$this->getRequest()->getParam('id', false);
73+
74+
return $categoryId ?: (int)$this->getRequest()->getParam('entity_id', false);
75+
}
76+
6577
/**
6678
* Build response for ajax request
6779
*

app/code/Magento/Catalog/Helper/Product/Compare.php

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -228,10 +228,9 @@ public function getRemoveUrl()
228228
*/
229229
public function getPostDataRemove($product)
230230
{
231-
$listCleanUrl = $this->getEncodedUrl($this->_getUrl('catalog/product_compare'));
232231
$data = [
233-
\Magento\Framework\App\ActionInterface::PARAM_NAME_URL_ENCODED => $listCleanUrl,
234-
'product' => $product->getId()
232+
\Magento\Framework\App\ActionInterface::PARAM_NAME_URL_ENCODED => '',
233+
'product' => $product->getId(),
235234
];
236235
return $this->postHelper->getPostData($this->getRemoveUrl(), $data);
237236
}
@@ -253,9 +252,8 @@ public function getClearListUrl()
253252
*/
254253
public function getPostDataClearList()
255254
{
256-
$refererUrl = $this->_getRequest()->getServer('HTTP_REFERER');
257255
$params = [
258-
\Magento\Framework\App\ActionInterface::PARAM_NAME_URL_ENCODED => $this->urlEncoder->encode($refererUrl)
256+
\Magento\Framework\App\ActionInterface::PARAM_NAME_URL_ENCODED => '',
259257
];
260258
return $this->postHelper->getPostData($this->getClearListUrl(), $params);
261259
}

app/code/Magento/Catalog/Model/Indexer/Category/Product/Action/Full.php

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,13 @@
77

88
class Full extends \Magento\Catalog\Model\Indexer\Category\Product\AbstractAction
99
{
10+
/**
11+
* Whether to use main or temporary index table
12+
*
13+
* @var bool
14+
*/
15+
protected $useTempTable = false;
16+
1017
/**
1118
* Refresh entities index
1219
*

app/code/Magento/Catalog/Model/ProductRepository.php

Lines changed: 13 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -313,15 +313,22 @@ protected function initializeProductData(array $productData, $createNew)
313313
*/
314314
private function assignProductToWebsites(\Magento\Catalog\Model\Product $product)
315315
{
316+
$websiteIds = $product->getWebsiteIds();
317+
316318
if (!$this->storeManager->hasSingleStore()) {
317-
if ($this->storeManager->getStore()->getCode() == \Magento\Store\Model\Store::ADMIN_CODE) {
318-
$websiteIds = array_keys($this->storeManager->getWebsites());
319-
} else {
320-
$websiteIds = [$this->storeManager->getStore()->getWebsiteId()];
321-
}
319+
$websiteIds = array_unique(
320+
array_merge(
321+
$websiteIds,
322+
[$this->storeManager->getStore()->getWebsiteId()]
323+
)
324+
);
325+
}
322326

323-
$product->setWebsiteIds(array_unique(array_merge($product->getWebsiteIds(), $websiteIds)));
327+
if ($this->storeManager->getStore(true)->getCode() == \Magento\Store\Model\Store::ADMIN_CODE) {
328+
$websiteIds = array_keys($this->storeManager->getWebsites());
324329
}
330+
331+
$product->setWebsiteIds($websiteIds);
325332
}
326333

327334
/**

app/code/Magento/Catalog/Model/ResourceModel/Category.php

Lines changed: 28 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,11 @@ class Category extends AbstractResource
3333
*/
3434
protected $_categoryProductTable;
3535

36+
/**
37+
* @var array[]
38+
*/
39+
private $entitiesWhereAttributesIs;
40+
3641
/**
3742
* Id of 'is_active' category attribute
3843
*
@@ -573,22 +578,29 @@ public function getIsActiveAttributeId()
573578
*/
574579
public function findWhereAttributeIs($entityIdsFilter, $attribute, $expectedValue)
575580
{
576-
$linkField = $this->getLinkField();
577-
$bind = ['attribute_id' => $attribute->getId(), 'value' => $expectedValue];
578-
$selectEntities = $this->getConnection()->select()->from(
579-
['ce' => $this->getTable('catalog_category_entity')],
580-
['entity_id']
581-
)->joinLeft(
582-
['ci' => $attribute->getBackend()->getTable()],
583-
"ci.{$linkField} = ce.{$linkField} AND attribute_id = :attribute_id",
584-
['value']
585-
)->where(
586-
'ci.value = :value'
587-
)->where(
588-
'ce.entity_id IN (?)',
589-
$entityIdsFilter
590-
);
591-
return $this->getConnection()->fetchCol($selectEntities, $bind);
581+
$entityIdsFilterHash = md5(serialize($entityIdsFilter));
582+
583+
if (!isset($this->entitiesWhereAttributesIs[$entityIdsFilterHash][$attribute->getId()][$expectedValue])) {
584+
$linkField = $this->getLinkField();
585+
$bind = ['attribute_id' => $attribute->getId(), 'value' => $expectedValue];
586+
$selectEntities = $this->getConnection()->select()->from(
587+
['ce' => $this->getTable('catalog_category_entity')],
588+
['entity_id']
589+
)->joinLeft(
590+
['ci' => $attribute->getBackend()->getTable()],
591+
"ci.{$linkField} = ce.{$linkField} AND attribute_id = :attribute_id",
592+
['value']
593+
)->where(
594+
'ci.value = :value'
595+
)->where(
596+
'ce.entity_id IN (?)',
597+
$entityIdsFilter
598+
);
599+
$this->entitiesWhereAttributesIs[$entityIdsFilterHash][$attribute->getId()][$expectedValue] =
600+
$this->getConnection()->fetchCol($selectEntities, $bind);
601+
}
602+
603+
return $this->entitiesWhereAttributesIs[$entityIdsFilterHash][$attribute->getId()][$expectedValue];
592604
}
593605

594606
/**

app/code/Magento/Catalog/Model/ResourceModel/MaxHeapTableSizeProcessor.php

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,9 @@
77

88
use Magento\Framework\App\ResourceConnection;
99

10+
/**
11+
* @deprecated
12+
*/
1013
class MaxHeapTableSizeProcessor
1114
{
1215
/**

app/code/Magento/Catalog/Plugin/Model/Indexer/Category/Product/MaxHeapTableSizeProcessorOnFullReindex.php

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,9 @@
1010
use Magento\Catalog\Model\ResourceModel\MaxHeapTableSizeProcessor;
1111
use Psr\Log\LoggerInterface;
1212

13+
/**
14+
* @deprecated
15+
*/
1316
class MaxHeapTableSizeProcessorOnFullReindex
1417
{
1518
/**

app/code/Magento/Catalog/Test/Unit/Helper/Product/CompareTest.php

Lines changed: 3 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -113,18 +113,13 @@ public function testGetPostDataRemove()
113113
//Data
114114
$productId = 1;
115115
$removeUrl = 'catalog/product_compare/remove';
116-
$compareListUrl = 'catalog/product_compare';
117116
$postParams = [
118-
Action::PARAM_NAME_URL_ENCODED => strtr(base64_encode($compareListUrl), '+/=', '-_,'),
117+
Action::PARAM_NAME_URL_ENCODED => '',
119118
'product' => $productId
120119
];
121120

122121
//Verification
123-
$this->urlBuilder->expects($this->at(0))
124-
->method('getUrl')
125-
->with($compareListUrl)
126-
->will($this->returnValue($compareListUrl));
127-
$this->urlBuilder->expects($this->at(1))
122+
$this->urlBuilder->expects($this->once())
128123
->method('getUrl')
129124
->with($removeUrl)
130125
->will($this->returnValue($removeUrl));
@@ -159,18 +154,12 @@ public function testGetClearListUrl()
159154
public function testGetPostDataClearList()
160155
{
161156
//Data
162-
$refererUrl = 'home/';
163157
$clearUrl = 'catalog/product_compare/clear';
164158
$postParams = [
165-
Action::PARAM_NAME_URL_ENCODED => strtr(base64_encode($refererUrl), '+/=', '-_,')
159+
Action::PARAM_NAME_URL_ENCODED => ''
166160
];
167161

168162
//Verification
169-
$this->request->expects($this->once())
170-
->method('getServer')
171-
->with('HTTP_REFERER')
172-
->will($this->returnValue($refererUrl));
173-
174163
$this->urlBuilder->expects($this->once())
175164
->method('getUrl')
176165
->with($clearUrl)

app/code/Magento/Catalog/Test/Unit/Model/ProductRepositoryTest.php

Lines changed: 50 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
use Magento\Framework\DB\Adapter\ConnectionException;
1515
use Magento\Framework\TestFramework\Unit\Helper\ObjectManager;
1616
use Magento\Framework\Api\SearchCriteria\CollectionProcessorInterface;
17+
use Magento\Store\Api\Data\StoreInterface;
1718

1819
/**
1920
* Class ProductRepositoryTest
@@ -284,7 +285,6 @@ protected function setUp()
284285
$storeMock->expects($this->any())->method('getWebsiteId')->willReturn('1');
285286
$storeMock->expects($this->any())->method('getCode')->willReturn(\Magento\Store\Model\Store::ADMIN_CODE);
286287
$this->storeManagerMock->expects($this->any())->method('getStore')->willReturn($storeMock);
287-
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
288288

289289
$this->mediaGalleryProcessor = $this->getMock(
290290
\Magento\Catalog\Model\Product\Gallery\Processor::class,
@@ -495,6 +495,7 @@ public function testGetBySkuFromCacheInitializedInGetById()
495495

496496
public function testSaveExisting()
497497
{
498+
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
498499
$this->resourceModelMock->expects($this->any())->method('getIdBySku')->will($this->returnValue(100));
499500
$this->productFactoryMock->expects($this->any())
500501
->method('create')
@@ -514,6 +515,7 @@ public function testSaveExisting()
514515

515516
public function testSaveNew()
516517
{
518+
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
517519
$this->resourceModelMock->expects($this->at(0))->method('getIdBySku')->will($this->returnValue(null));
518520
$this->resourceModelMock->expects($this->at(3))->method('getIdBySku')->will($this->returnValue(100));
519521
$this->productFactoryMock->expects($this->any())
@@ -538,6 +540,7 @@ public function testSaveNew()
538540
*/
539541
public function testSaveUnableToSaveException()
540542
{
543+
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
541544
$this->resourceModelMock->expects($this->exactly(1))->method('getIdBySku')->will($this->returnValue(null));
542545
$this->productFactoryMock->expects($this->exactly(2))
543546
->method('create')
@@ -562,6 +565,7 @@ public function testSaveUnableToSaveException()
562565
*/
563566
public function testSaveException()
564567
{
568+
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
565569
$this->resourceModelMock->expects($this->exactly(1))->method('getIdBySku')->will($this->returnValue(null));
566570
$this->productFactoryMock->expects($this->exactly(2))
567571
->method('create')
@@ -587,6 +591,7 @@ public function testSaveException()
587591
*/
588592
public function testSaveInvalidProductException()
589593
{
594+
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
590595
$this->resourceModelMock->expects($this->exactly(1))->method('getIdBySku')->will($this->returnValue(null));
591596
$this->productFactoryMock->expects($this->exactly(2))
592597
->method('create')
@@ -610,6 +615,7 @@ public function testSaveInvalidProductException()
610615
*/
611616
public function testSaveThrowsTemporaryStateExceptionIfDatabaseConnectionErrorOccurred()
612617
{
618+
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
613619
$this->productFactoryMock->expects($this->any())
614620
->method('create')
615621
->will($this->returnValue($this->productMock));
@@ -796,6 +802,7 @@ public function cacheKeyDataProvider()
796802
*/
797803
public function testSaveExistingWithOptions(array $newOptions, array $existingOptions, array $expectedData)
798804
{
805+
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
799806
$this->resourceModelMock->expects($this->any())->method('getIdBySku')->will($this->returnValue(100));
800807
$this->productFactoryMock->expects($this->any())
801808
->method('create')
@@ -964,6 +971,7 @@ public function saveExistingWithOptionsDataProvider()
964971
*/
965972
public function testSaveWithLinks(array $newLinks, array $existingLinks, array $expectedData)
966973
{
974+
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
967975
$this->resourceModelMock->expects($this->any())->method('getIdBySku')->will($this->returnValue(100));
968976
$this->productFactoryMock->expects($this->any())
969977
->method('create')
@@ -1143,6 +1151,7 @@ protected function setupProductMocksForSave()
11431151

11441152
public function testSaveExistingWithNewMediaGalleryEntries()
11451153
{
1154+
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
11461155
$newEntriesData = [
11471156
[
11481157
"label" => "label_text",
@@ -1222,8 +1231,48 @@ public function testSaveExistingWithNewMediaGalleryEntries()
12221231
$this->model->save($this->productMock);
12231232
}
12241233

1234+
public function websitesProvider()
1235+
{
1236+
return [
1237+
[[1,2,3]]
1238+
];
1239+
}
1240+
1241+
public function testSaveWithDifferentWebsites()
1242+
{
1243+
$storeMock = $this->getMock(StoreInterface::class);
1244+
$this->resourceModelMock->expects($this->at(0))->method('getIdBySku')->will($this->returnValue(null));
1245+
$this->resourceModelMock->expects($this->at(3))->method('getIdBySku')->will($this->returnValue(100));
1246+
$this->productFactoryMock->expects($this->any())
1247+
->method('create')
1248+
->will($this->returnValue($this->productMock));
1249+
$this->initializationHelperMock->expects($this->never())->method('initialize');
1250+
$this->resourceModelMock->expects($this->once())->method('validate')->with($this->productMock)
1251+
->willReturn(true);
1252+
$this->resourceModelMock->expects($this->once())->method('save')->with($this->productMock)->willReturn(true);
1253+
$this->extensibleDataObjectConverterMock
1254+
->expects($this->once())
1255+
->method('toNestedArray')
1256+
->will($this->returnValue($this->productData));
1257+
$this->storeManagerMock->expects($this->any())
1258+
->method('getStore')
1259+
->willReturn($storeMock);
1260+
$this->storeManagerMock->expects($this->once())
1261+
->method('getWebsites')
1262+
->willReturn([
1263+
1 => ['first'],
1264+
2 => ['second'],
1265+
3 => ['third']
1266+
]);
1267+
$this->productMock->expects($this->once())->method('getWebsiteIds')->willReturn([1,2,3]);
1268+
$this->productMock->expects($this->once())->method('setWebsiteIds')->willReturn([2,3]);
1269+
1270+
$this->assertEquals($this->productMock, $this->model->save($this->productMock));
1271+
}
1272+
12251273
public function testSaveExistingWithMediaGalleryEntries()
12261274
{
1275+
$this->storeManagerMock->expects($this->any())->method('getWebsites')->willReturn([1 => 'default']);
12271276
//update one entry, delete one entry
12281277
$newEntries = [
12291278
[

app/code/Magento/Catalog/etc/adminhtml/di.xml

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -73,7 +73,6 @@
7373
</type>
7474
<type name="Magento\Catalog\Model\Indexer\Category\Product\Action\Full">
7575
<plugin name="invalidate_pagecache_after_full_reindex" type="Magento\Catalog\Plugin\Model\Indexer\Category\Product\Execute" />
76-
<plugin name="max_heap_tablse_size_processor_on_full_reindex" type="Magento\Catalog\Plugin\Model\Indexer\Category\Product\MaxHeapTableSizeProcessorOnFullReindex"/>
7776
</type>
7877
<type name="Magento\Catalog\Model\ResourceModel\Attribute">
7978
<plugin name="invalidate_pagecache_after_attribute_save" type="Magento\Catalog\Plugin\Model\ResourceModel\Attribute\Save" />

0 commit comments

Comments
 (0)