Last active
April 28, 2023 12:24
-
-
Save sandipklevu/872979d8c3a2166245d71730f101ecd1 to your computer and use it in GitHub Desktop.
Gist for Klevu module 3.2.1 to trouble shoot debug issue
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env php | |
<?php | |
use Klevu\Search\Api\KlevuSyncRepositoryInterface; | |
use Klevu\Search\Api\MagentoProductSyncRepositoryInterface; | |
use Klevu\Search\Model\Klevu\Klevu; | |
use Magento\Eav\Model\Entity; | |
use Magento\Framework\App\Bootstrap; | |
use Magento\Store\Api\Data\StoreInterface; | |
if (PHP_SAPI !== 'cli') { | |
echo 'bin/klevu-sync-debug must be run as a CLI application'; | |
exit(1); | |
} | |
$storeCode = isset($argv[1]) | |
? trim((string)$argv[1]) | |
: null; | |
if (!$storeCode) { | |
echo 'Please specify a store code'; | |
exit(1); | |
} | |
try { | |
require __DIR__ . '/../app/bootstrap.php'; | |
$bootstrap = Bootstrap::create(BP, $_SERVER); | |
$objectManager = $bootstrap->getObjectManager(); | |
/** @var \Magento\Store\Model\StoreManagerInterface $storeManager */ | |
$storeManager = $objectManager->get(\Magento\Store\Model\StoreManagerInterface::class); | |
} catch (\Exception $e) { | |
echo 'Autoload error: ' . $e->getMessage(); | |
exit(1); | |
} | |
try { | |
$store = $storeManager->getStore($storeCode); | |
$storeId = (int)$store->getId(); | |
} catch (\Exception $e) { | |
echo 'Error loading store: ' . $e->getMessage(); | |
exit(1); | |
} | |
function diffMultiDimensionalArrays(array $array1, array $array2) | |
{ | |
$jsonDiff = array_diff( | |
array_map('json_encode', $array1), | |
array_map('json_encode', $array2) | |
); | |
return array_map('json_decode', $jsonDiff); | |
} | |
/** | |
* @param $storeId | |
* @param $productIds | |
* @param $skipChildProducts | |
* @param $includeOosParents | |
* @param $magentoProductSyncRepository | |
* | |
* @return array | |
*/ | |
function formatMagentoProductIds( | |
$storeId, | |
$productIds = [], | |
$skipChildProducts = false, | |
$includeOosParents = true, | |
$magentoProductSyncRepository | |
) { | |
$magentoProductIds = []; | |
if (!$productIds) { | |
return $magentoProductIds; | |
} | |
// getParentRelationsByChild | |
// $parentIds = $this->getParentRelationsByChild($productIds, $storeId, $includeOosParents); | |
$list = $magentoProductSyncRepository->getParentProductRelations($productIds, $storeId, $includeOosParents); | |
$parentIds = []; | |
foreach ($list as $row) { | |
if (!isset($parentIds[$row['product_id']])) { | |
$parentIds[$row['product_id']] = []; | |
} | |
$parentIds[$row['product_id']][] = $row; | |
} | |
unset($list); | |
// end getParentRelationsByChild | |
foreach ($productIds as $entityId) { | |
$entityParentIds = isset($parentIds[$entityId]) | |
? $parentIds[$entityId] | |
: []; | |
foreach ($entityParentIds as $entityParentId) { | |
$magentoProductIds[] = [ | |
'product_id' => $entityId, | |
'parent_id' => $entityParentId[Entity::DEFAULT_ENTITY_ID_FIELD], | |
]; | |
} | |
if ($skipChildProducts) { | |
continue; | |
} | |
$magentoProductIds[] = [ | |
'product_id' => $entityId, | |
'parent_id' => \Klevu\Search\Model\Product\MagentoProductActions::PARENT_ID_WHEN_NOT_VISIBLE, | |
]; | |
} | |
unset($parentIds); | |
return $magentoProductIds; | |
} | |
/** | |
* As per 3.2.1 klevu module | |
* | |
* @param array $productIdsToDelete | |
* @param StoreInterface $store | |
* @param $includeOosProducts | |
* @param $magentoProductSyncRepository | |
* | |
* @return array | |
*/ | |
function formatProductIdsToDelete( | |
array $productIdsToDelete, | |
StoreInterface $store, | |
$includeOosProducts = true, | |
$magentoProductSyncRepository | |
) { | |
$return = []; | |
/** @var MagentoProductSyncRepositoryInterface $magentoProductSyncRepository */ | |
$parentProductIds = $magentoProductSyncRepository->getParentProductIds($store, $includeOosProducts); | |
foreach ($productIdsToDelete as $productIds) { | |
$productIds = (array)$productIds; | |
$parentId = $productIds[\Klevu\Search\Model\Klevu\Klevu::FIELD_PARENT_ID]; | |
$productId = $productIds[\Klevu\Search\Model\Klevu\Klevu::FIELD_PRODUCT_ID]; | |
$return[$parentId . '-' . $productId] = [ | |
'parent_id' => $parentId, | |
'product_id' => $productId, | |
]; | |
if (!(int)$parentId || ($parentId && in_array($parentId, $parentProductIds, true)) | |
) { | |
continue; | |
} | |
$return[$productId] = [ | |
'parent_id' => $parentId, | |
'product_id' => $productId, | |
]; | |
} | |
return $return; | |
} | |
/** @var Magento\Framework\App\State $appState */ | |
$appState = $objectManager->get(\Magento\Framework\App\State::class); | |
$appState->setAreaCode('frontend'); | |
/** @var Magento\Store\Model\StoreManagerInterface $storeManager */ | |
$storeManager = $objectManager->get(\Magento\Store\Model\StoreManagerInterface::class); | |
$storeManager->setCurrentStore($store); | |
/** @var KlevuSyncRepositoryInterface $klevuSyncRepository */ | |
$klevuSyncRepository = $objectManager->get(KlevuSyncRepositoryInterface::class); | |
/** @var MagentoProductSyncRepositoryInterface $magentoProductSyncRepository */ | |
$magentoProductSyncRepository = $objectManager->get(MagentoProductSyncRepositoryInterface::class); | |
/** @var \Klevu\Search\Model\Product\MagentoProductActionsInterface $magentoProductActions */ | |
$magentoProductActions = $objectManager->get(\Klevu\Search\Model\Product\MagentoProductActionsInterface::class); | |
/** @var \Klevu\Search\Model\Klevu\ResourceModel\Klevu\Collection $klevuResourceCollection */ | |
$klevuResourceCollection = $objectManager->get(\Klevu\Search\Model\Klevu\ResourceModel\Klevu\Collection::class); | |
/** @var \Klevu\Search\Helper\Config $klevuHelperConfig */ | |
$klevuHelperConfig = $objectManager->get(\Klevu\Search\Helper\Config::class); | |
$includeOosProductsInSync = $klevuHelperConfig->includeOosProductsInSync($store); | |
/** @var \Klevu\Search\Model\Product\LoadAttribute $loadAttribute */ | |
$loadAttribute = $objectManager->get(\Klevu\Search\Model\Product\LoadAttribute::class); | |
/** | |
* 3.2.1 | |
* @param array $productIdsToAdd | |
* @param StoreInterface $store | |
* @param $includeOosProducts | |
* @param $magentoProductSyncRepository | |
* | |
* @return array | |
*/ | |
function formatProductIdsToAdd( | |
array $productIdsToAdd, | |
StoreInterface $store, | |
$includeOosProducts = true, | |
$magentoProductSyncRepository | |
) { | |
$productsIds = []; | |
$parentProductIds = $magentoProductSyncRepository->getParentProductIds($store, $includeOosProducts); | |
foreach ($productIdsToAdd as $productIds) { | |
$productIds = (array)$productIds; | |
$parentId = $productIds[\Klevu\Search\Model\Klevu\Klevu::FIELD_PARENT_ID]; | |
$productId = $productIds[\Klevu\Search\Model\Klevu\Klevu::FIELD_PRODUCT_ID]; | |
if ((int)$parentId && !in_array($parentId, $parentProductIds, true) | |
) { | |
continue; | |
} | |
$productsIds[$parentId . '-' . $productId] = [ | |
'parent_id' => $parentId, | |
'product_id' => $productId, | |
]; | |
} | |
return $productsIds; | |
} | |
$productIds = [ | |
'delete' => $magentoProductActions->deleteProductCollection($store), | |
'update' => $magentoProductActions->updateProductCollection($store), | |
'add' => $magentoProductActions->addProductCollection($store), | |
]; | |
$maxSyncIds = [ | |
'delete' => $klevuSyncRepository->getMaxSyncId($store), | |
'update' => $klevuSyncRepository->getMaxSyncId($store), | |
'add' => $magentoProductSyncRepository->getMaxProductId($store), | |
]; | |
$colWidths = [20, 15, 15]; | |
$divider = sprintf( | |
'+%s+%s+%s+', | |
str_repeat('-', $colWidths[0]), | |
str_repeat('-', $colWidths[1]), | |
str_repeat('-', $colWidths[2]) | |
); | |
echo "ACTIONS SUMMARY" . PHP_EOL; | |
echo $divider . PHP_EOL; | |
echo sprintf( | |
'|%s|%s|%s|', | |
str_pad(' ACTION ', $colWidths[0], ' ', STR_PAD_RIGHT), | |
str_pad(' COUNT ', $colWidths[1], ' ', STR_PAD_LEFT), | |
str_pad(' MAX SYNC ID ', $colWidths[1], ' ', STR_PAD_LEFT) | |
) . PHP_EOL; | |
foreach ($maxSyncIds as $action => $maxSyncId) { | |
echo $divider . PHP_EOL; | |
echo sprintf( | |
'|%s|%s|%s|', | |
str_pad(' ' . $action . ' ', $colWidths[0], ' ', STR_PAD_RIGHT), | |
str_pad(' ' . number_format(count($productIds[$action])) . ' ', $colWidths[1], ' ', STR_PAD_LEFT), | |
str_pad(' ' . $maxSyncId . ' ', $colWidths[1], ' ', STR_PAD_LEFT) | |
) . PHP_EOL; | |
} | |
echo $divider . PHP_EOL; | |
echo PHP_EOL; | |
echo "PRODUCT IDS FOR ACTION" . PHP_EOL; | |
echo $divider . PHP_EOL; | |
echo sprintf( | |
'|%s|%s|%s|', | |
str_pad(' IDENTIFIER ', $colWidths[0], ' ', STR_PAD_RIGHT), | |
str_pad(' PARENT_ID ', $colWidths[1], ' ', STR_PAD_LEFT), | |
str_pad(' PRODUCT_ID ', $colWidths[1], ' ', STR_PAD_LEFT) | |
) . PHP_EOL; | |
foreach ($productIds as $rowTitle => $rowData) { | |
echo $divider . PHP_EOL; | |
echo sprintf('| %s |', str_pad($rowTitle, array_sum($colWidths))) . PHP_EOL; | |
foreach ($rowData as $identifier => $row) { | |
echo $divider . PHP_EOL; | |
echo sprintf( | |
'|%s|%s|%s|', | |
str_pad(' ' . $identifier . ' ', $colWidths[0], ' ', STR_PAD_RIGHT), | |
str_pad(' ' . $row['parent_id'] . ' ', $colWidths[1], ' ', STR_PAD_LEFT), | |
str_pad(' ' . $row['product_id'] . ' ', $colWidths[1], ' ', STR_PAD_LEFT) | |
) . PHP_EOL; | |
} | |
} | |
echo $divider . PHP_EOL; | |
echo PHP_EOL . PHP_EOL; | |
echo "PARENT PRODUCT IDS" . PHP_EOL; | |
$parentProductIds = $magentoProductSyncRepository->getParentProductIds($store); | |
echo implode(',', $parentProductIds) . PHP_EOL; | |
echo PHP_EOL . PHP_EOL; | |
// -- deleteProductCollection | |
echo "deleteProductCollection" . PHP_EOL; | |
echo "--------------------" . PHP_EOL . PHP_EOL; | |
$maxEntityId = $maxSyncIds['delete']; | |
if ($maxEntityId) { | |
$klevuSyncRepository->clearKlevuCollection(); | |
$lastEntityId = 0; | |
$i = 0; | |
while ($lastEntityId < $maxEntityId) { | |
echo "Iteration: " . $i . PHP_EOL; | |
echo "- Max Entity Id: " . $maxEntityId . PHP_EOL; | |
echo "- Last Entity Id: " . $lastEntityId . PHP_EOL; | |
$klevuProductIds = $klevuSyncRepository->getProductIds($store, [], $lastEntityId); | |
echo "- Klevu Product Ids (" . count($klevuProductIds) . "): " . implode(',', | |
array_map('json_encode', $klevuProductIds)) . PHP_EOL; | |
if (!$klevuProductIds || ++$i >= \Klevu\Search\Model\Product\MagentoProductActions::MAX_ITERATIONS) { | |
echo PHP_EOL; | |
echo "* Exiting loop" . PHP_EOL; | |
break; | |
} | |
$lastEntityId = (int)max(array_column($klevuProductIds, \Klevu\Search\Model\Klevu\Klevu::FIELD_ENTITY_ID)); | |
$productIdsToFilter = array_map(static function (array $product) { | |
return $product['product_id']; | |
}, $klevuProductIds); | |
array_walk($klevuProductIds, function (&$v) { | |
unset($v['row_id']); | |
}); | |
echo "- Product Ids to Filter (" . count($productIdsToFilter) . "): " . implode(',', $productIdsToFilter) | |
. PHP_EOL; | |
$magentoProductIdsCollection = $magentoProductSyncRepository->getProductIdsCollection( | |
$store, | |
MagentoProductSyncRepositoryInterface::NOT_VISIBLE_INCLUDED | |
); | |
echo PHP_EOL . "- getProductIdsCollection Query: " . PHP_EOL . | |
$magentoProductIdsCollection->getSelect()->__toString() | |
. PHP_EOL; | |
echo "- Magento Product Ids Collection (" . $magentoProductIdsCollection->count() . "): " . implode(',', | |
$magentoProductIdsCollection->getColumnValues('entity_id')) . PHP_EOL; | |
$magentoProductIds = $magentoProductSyncRepository->getBatchDataForCollection( | |
$magentoProductIdsCollection, | |
$store, | |
$productIdsToFilter, | |
null | |
); | |
echo "- Magento Product Ids (" . count($magentoProductIds) . "): " . implode(',', $magentoProductIds) . PHP_EOL; | |
$magentoProductIds = formatMagentoProductIds( | |
$storeId, | |
$magentoProductIds, | |
false, | |
$includeOosProductsInSync, | |
$magentoProductSyncRepository | |
); | |
echo "- Magento Product Ids - after format (" . count($magentoProductIds) . "): " | |
. json_encode($magentoProductIds) . PHP_EOL; | |
$productIdsDiff = diffMultiDimensionalArrays($klevuProductIds, $magentoProductIds); | |
echo "- Product Ids Diff (" . count($productIdsDiff) . "): " . json_encode($productIdsDiff) . PHP_EOL; | |
$formattedProductIdsToDelete = formatProductIdsToDelete($productIdsDiff, | |
$store, | |
$includeOosProductsInSync, | |
$magentoProductSyncRepository); | |
echo "- Formatted Product Ids to Delete (" . count($formattedProductIdsToDelete) . "): " | |
. json_encode($formattedProductIdsToDelete) . PHP_EOL; | |
echo PHP_EOL . "-----" . PHP_EOL; | |
} | |
} else { | |
echo "No max entity for delete operation" . PHP_EOL; | |
} | |
echo PHP_EOL . PHP_EOL; | |
// -- updateProductCollection | |
echo "updateProductCollection" . PHP_EOL; | |
echo "--------------------" . PHP_EOL . PHP_EOL; | |
echo "SQL Query for filterProductsToUpdate: " . $klevuResourceCollection->filterProductsToUpdate()->getSelect()->__toString() . PHP_EOL; | |
$maxEntityId = $maxSyncIds['update']; | |
$klevuToUpdate = []; | |
if ($maxEntityId) { | |
$klevuSyncRepository->clearKlevuCollection(); | |
$lastEntityId = 0; | |
$i = 0; | |
while ($lastEntityId < $maxEntityId) { | |
echo "Iteration: " . $i . PHP_EOL; | |
echo "- Max Entity ID: " . $maxEntityId . PHP_EOL; | |
echo "- Last Entity ID: " . $lastEntityId . PHP_EOL; | |
$klevuProductIds = $klevuSyncRepository->getProductIdsForUpdate( | |
$store, | |
$productIds['update'], | |
$lastEntityId | |
); | |
echo "- Klevu Product Ids (updateProductCollection) (" . count($klevuProductIds) . "): " . implode(',', | |
array_map('json_encode', $klevuProductIds)) . PHP_EOL; | |
if (!$klevuProductIds || ++$i >= \Klevu\Search\Model\Product\MagentoProductActions::MAX_ITERATIONS) { | |
echo PHP_EOL; | |
echo "* updateProductCollection Exiting loop" . PHP_EOL; | |
break; | |
} | |
$lastEntityId = (int)max(array_column( | |
$klevuProductIds, | |
\Klevu\Search\Model\Klevu\Klevu::FIELD_ENTITY_ID) | |
); | |
foreach ($klevuProductIds as $klevuItem) { | |
$parentFieldId = $klevuItem[\Klevu\Search\Model\Klevu\Klevu::FIELD_PARENT_ID]; | |
$productFieldId = $klevuItem[\Klevu\Search\Model\Klevu\Klevu::FIELD_PRODUCT_ID]; | |
$uniqueGroupKey = $parentFieldId . "-" . $productFieldId; | |
$klevuToUpdate[$uniqueGroupKey]["product_id"] = $productFieldId; | |
$klevuToUpdate[$uniqueGroupKey]["parent_id"] = $parentFieldId; | |
} | |
echo "- Klevu Product Ids - updateProductCollection (" . count($klevuToUpdate) . "): " . implode(',', | |
array_map('json_encode', $klevuToUpdate)) . PHP_EOL; | |
echo PHP_EOL . "-----" . PHP_EOL; | |
} | |
} else { | |
echo "No max entity for update operation" . PHP_EOL; | |
} | |
// -- addProductCollection | |
echo PHP_EOL . PHP_EOL; | |
echo "addProductCollection" . PHP_EOL; | |
echo "--------------------" . PHP_EOL . PHP_EOL; | |
$maxEntityId = $maxSyncIds['add']; | |
if ($maxEntityId) { | |
$klevuSyncRepository->clearKlevuCollection(); | |
$batchedProductIds = []; | |
$productCollection = $magentoProductSyncRepository->getProductIdsCollection($store); | |
echo PHP_EOL . "- AddProductCollection (getProductIdsCollection): SQL Query: " . PHP_EOL | |
. $productCollection->getSelect() | |
->__toString() | |
. PHP_EOL; | |
$childProductCollection = $magentoProductSyncRepository->getChildProductIdsCollection($store); | |
echo PHP_EOL . "- AddProductCollection (getChildProductIdsCollection): SQL Query: " . PHP_EOL | |
. $childProductCollection->getSelect()->__toString() | |
. PHP_EOL; | |
$lastProductEntityId = 0; | |
$lastChildEntityId = 0; | |
$i = 0; | |
while ($lastProductEntityId < $maxEntityId || $lastChildEntityId < $maxEntityId) { | |
echo "Iteration: " . $i . PHP_EOL; | |
echo "- Max Entity ID : " . $maxEntityId . PHP_EOL; | |
echo "- Last Product Entity ID : " . $lastProductEntityId . PHP_EOL; | |
echo "- Last Child Entity ID : " . $lastChildEntityId . PHP_EOL; | |
$productIds = ($lastProductEntityId < $maxEntityId) | |
? | |
$magentoProductSyncRepository->getBatchDataForCollection($productCollection, | |
$store, | |
[], | |
$lastProductEntityId) | |
: | |
[]; | |
echo "- Product Ids (" . count($productIds) . "): " . implode(',', $productIds) . PHP_EOL; | |
$childProductIds = ($lastChildEntityId < $maxEntityId) | |
? | |
$magentoProductSyncRepository->getBatchDataForCollection($childProductCollection, | |
$store, | |
[], | |
$lastChildEntityId) | |
: | |
[]; | |
echo "- Child Product Ids (" . count($childProductIds) . "): " . implode(',', $childProductIds) . PHP_EOL; | |
if ((!$productIds && !$childProductIds) | |
|| ++$i >= \Klevu\Search\Model\Product\MagentoProductActions::MAX_ITERATIONS) { | |
echo PHP_EOL; | |
echo "* Exiting loop" . PHP_EOL; | |
break; | |
} | |
$lastProductEntityId = $productIds | |
? (int)max($productIds) | |
: $maxEntityId + 1; | |
$lastChildEntityId = $childProductIds | |
? (int)max($childProductIds) | |
: $maxEntityId + 1; | |
$magentoProductIdsToFilter = array_merge($productIds, $childProductIds); | |
echo "- Magento Product Ids To Filter (" . count($magentoProductIdsToFilter) . "): " . implode(',', | |
$magentoProductIdsToFilter) . PHP_EOL; | |
$magentoProductIds = array_merge( | |
formatMagentoProductIds($storeId, | |
$productIds, | |
false, | |
$includeOosProductsInSync, | |
$magentoProductSyncRepository | |
), | |
formatMagentoProductIds($storeId, | |
$childProductIds, | |
true, | |
$includeOosProductsInSync, | |
$magentoProductSyncRepository) | |
); | |
echo "- Magento Product Ids (" . count($magentoProductIds) . "): " . json_encode($magentoProductIds) . PHP_EOL; | |
$klevuProductIds = $klevuSyncRepository->getProductIds($store, $magentoProductIdsToFilter); | |
echo "- Klevu Product Ids (" . count($klevuProductIds) . "): " . json_encode($klevuProductIds) . PHP_EOL; | |
array_walk($klevuProductIds, function (&$v) { | |
unset($v['row_id']); | |
}); | |
$productIdsDiff = diffMultiDimensionalArrays($magentoProductIds, $klevuProductIds); | |
echo "- Product Ids Diff (" . count($productIdsDiff) . "): " . json_encode($productIdsDiff) . PHP_EOL; | |
$formattedProductIdsToAdd = formatProductIdsToAdd($productIdsDiff, | |
$store, | |
$includeOosProductsInSync, | |
$magentoProductSyncRepository); | |
echo "- Formatted Product Ids to Add (" . count($formattedProductIdsToAdd) . "): " | |
. json_encode($formattedProductIdsToAdd) . PHP_EOL; | |
$loadAttributeCollection = $loadAttribute->loadProductDataCollection($formattedProductIdsToAdd, $storeId); | |
echo "- LoadAttributeCollection SQL Query : " . PHP_EOL . | |
$loadAttributeCollection->getSelect()->__toString() | |
. PHP_EOL; | |
echo PHP_EOL . "-----" . PHP_EOL; | |
} | |
} else { | |
echo "No max entity for add operation" . PHP_EOL; | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment