Skip to content
This repository was archived by the owner on Apr 29, 2019. It is now read-only.

Commit 461009e

Browse files
author
Oleksandr Gorkun
committed
MAGETWO-72864: Impossible to export Advanced Prices on a medium profile
1 parent 4979ddd commit 461009e

File tree

2 files changed

+259
-47
lines changed

2 files changed

+259
-47
lines changed

app/code/Magento/AdvancedPricingImportExport/Model/Export/AdvancedPricing.php

Lines changed: 226 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
*/
66
namespace Magento\AdvancedPricingImportExport\Model\Export;
77

8+
use Magento\ImportExport\Model\Export;
89
use Magento\Store\Model\Store;
910
use Magento\CatalogImportExport\Model\Import\Product as ImportProduct;
1011
use Magento\AdvancedPricingImportExport\Model\Import\AdvancedPricing as ImportAdvancedPricing;
@@ -79,6 +80,11 @@ class AdvancedPricing extends \Magento\CatalogImportExport\Model\Export\Product
7980
ImportAdvancedPricing::COL_TIER_PRICE_TYPE => ''
8081
];
8182

83+
/**
84+
* @var string[]
85+
*/
86+
private $websiteCodesMap = [];
87+
8288
/**
8389
* @param \Magento\Framework\Stdlib\DateTime\TimezoneInterface $localeDate
8490
* @param \Magento\Eav\Model\Config $config
@@ -255,36 +261,139 @@ public function filterAttributeCollection(\Magento\Eav\Model\ResourceModel\Entit
255261
*/
256262
protected function getExportData()
257263
{
264+
if ($this->_passTierPrice) {
265+
return [];
266+
}
267+
258268
$exportData = [];
259269
try {
260-
$rawData = $this->collectRawData();
261-
$productIds = array_keys($rawData);
262-
if (isset($productIds)) {
263-
if (!$this->_passTierPrice) {
264-
$exportData = array_merge(
265-
$exportData,
266-
$this->getTierPrices($productIds, ImportAdvancedPricing::TABLE_TIER_PRICE)
267-
);
270+
$productsByStores = $this->loadCollection();
271+
if (!empty($productsByStores)) {
272+
$productLinkField = $this->getProductEntityLinkField();
273+
$anyStoreId = Store::DEFAULT_STORE_ID;
274+
275+
$productLinkIds = array_map(
276+
function (array $productData) use (
277+
$anyStoreId,
278+
$productLinkField
279+
) {
280+
return $productData[$anyStoreId][$productLinkField];
281+
},
282+
$productsByStores
283+
);
284+
$productLinkIds = array_unique($productLinkIds);
285+
$tierPricesData = $this->fetchTierPrices($productLinkIds);
286+
$exportData = $this->prepareExportData(
287+
$productsByStores,
288+
$tierPricesData
289+
);
290+
if (!empty($exportData)) {
291+
asort($exportData);
268292
}
269293
}
270-
if ($exportData) {
271-
$exportData = $this->correctExportData($exportData);
272-
}
273-
if (isset($exportData)) {
274-
asort($exportData);
275-
}
276-
} catch (\Exception $e) {
294+
} catch (\Throwable $e) {
277295
$this->_logger->critical($e);
278296
}
297+
279298
return $exportData;
280299
}
281300

301+
/**
302+
* Creating export-formatted row from tier price.
303+
*
304+
* @param array $tierPriceData Tier price information.
305+
*
306+
* @return array Formatted for export tier price information.
307+
*/
308+
private function createExportRow(array $tierPriceData): array
309+
{
310+
//List of columns to display in export row.
311+
$exportRow = $this->templateExportData;
312+
313+
foreach (array_keys($exportRow) as $keyTemplate) {
314+
if (array_key_exists($keyTemplate, $tierPriceData)) {
315+
if (in_array($keyTemplate, $this->_priceWebsite)) {
316+
//If it's website column then getting website code.
317+
$exportRow[$keyTemplate] = $this->_getWebsiteCode(
318+
$tierPriceData[$keyTemplate]
319+
);
320+
} elseif (in_array($keyTemplate, $this->_priceCustomerGroup)) {
321+
//If it's customer group column then getting customer
322+
//group name by ID.
323+
$exportRow[$keyTemplate] = $this->_getCustomerGroupById(
324+
$tierPriceData[$keyTemplate],
325+
$tierPriceData[ImportAdvancedPricing::VALUE_ALL_GROUPS]
326+
);
327+
unset($exportRow[ImportAdvancedPricing::VALUE_ALL_GROUPS]);
328+
} elseif ($keyTemplate
329+
=== ImportAdvancedPricing::COL_TIER_PRICE
330+
) {
331+
//If it's price column then getting value and type
332+
//of tier price.
333+
$exportRow[$keyTemplate]
334+
= $tierPriceData[ImportAdvancedPricing::COL_TIER_PRICE_PERCENTAGE_VALUE]
335+
? $tierPriceData[ImportAdvancedPricing::COL_TIER_PRICE_PERCENTAGE_VALUE]
336+
: $tierPriceData[ImportAdvancedPricing::COL_TIER_PRICE];
337+
$exportRow[ImportAdvancedPricing::COL_TIER_PRICE_TYPE]
338+
= $this->tierPriceTypeValue($tierPriceData);
339+
} else {
340+
//Any other column just goes as is.
341+
$exportRow[$keyTemplate] = $tierPriceData[$keyTemplate];
342+
}
343+
}
344+
}
345+
346+
return $exportRow;
347+
}
348+
349+
/**
350+
* Prepare data for export.
351+
*
352+
* @param array $productsData Products to export.
353+
* @param array $tierPricesData Their tier prices.
354+
*
355+
* @return array Export rows to display.
356+
*/
357+
private function prepareExportData(
358+
array $productsData,
359+
array $tierPricesData
360+
): array {
361+
//Assigning SKUs to tier prices data.
362+
$productLinkIdToSkuMap = [];
363+
foreach ($productsData as $productData) {
364+
$productLinkIdToSkuMap[$productData[Store::DEFAULT_STORE_ID][$this->getProductEntityLinkField()]]
365+
= $productData[Store::DEFAULT_STORE_ID]['sku'];
366+
}
367+
unset($productData);
368+
369+
//Adding products' SKUs to tier price data.
370+
$linkedTierPricesData = [];
371+
foreach ($tierPricesData as $tierPriceData) {
372+
$sku = $productLinkIdToSkuMap[$tierPriceData['product_link_id']];
373+
$linkedTierPricesData[] = array_merge(
374+
$tierPriceData,
375+
[ImportAdvancedPricing::COL_SKU => $sku]
376+
);
377+
}
378+
unset($sku, $tierPriceData);
379+
380+
//Formatting data for export.
381+
$customExportData = [];
382+
foreach ($linkedTierPricesData as $row) {
383+
$customExportData[] = $this->createExportRow($row);
384+
}
385+
386+
return $customExportData;
387+
}
388+
282389
/**
283390
* Correct export data.
284391
*
285392
* @param array $exportData
286393
* @return array
287394
* @SuppressWarnings(PHPMD.UnusedLocalVariable)
395+
* @deprecated
396+
* @see prepareExportData
288397
*/
289398
protected function correctExportData($exportData)
290399
{
@@ -327,16 +436,82 @@ protected function correctExportData($exportData)
327436
/**
328437
* Check type for tier price.
329438
*
330-
* @param string $tierPricePercentage
439+
* @param array $tierPriceData
331440
* @return string
332441
*/
333-
private function tierPriceTypeValue($tierPricePercentage)
442+
private function tierPriceTypeValue(array $tierPriceData): string
334443
{
335-
return $tierPricePercentage
444+
return $tierPriceData[ImportAdvancedPricing::COL_TIER_PRICE_PERCENTAGE_VALUE]
336445
? ImportAdvancedPricing::TIER_PRICE_TYPE_PERCENT
337446
: ImportAdvancedPricing::TIER_PRICE_TYPE_FIXED;
338447
}
339448

449+
/**
450+
* Load tier prices for given products.
451+
*
452+
* @param string[] $productIds Link IDs of products to find tier prices for.
453+
*
454+
* @return array Tier prices data.
455+
*/
456+
private function fetchTierPrices(array $productIds): array
457+
{
458+
if (empty($productIds)) {
459+
throw new \InvalidArgumentException(
460+
'Can only load tier prices for specific products'
461+
);
462+
}
463+
464+
$pricesTable = ImportAdvancedPricing::TABLE_TIER_PRICE;
465+
$exportFilter = null;
466+
$priceFromFilter = null;
467+
$priceToFilter = null;
468+
if (isset($this->_parameters[Export::FILTER_ELEMENT_GROUP])) {
469+
$exportFilter = $this->_parameters[Export::FILTER_ELEMENT_GROUP];
470+
}
471+
$productEntityLinkField = $this->getProductEntityLinkField();
472+
$selectFields = [
473+
ImportAdvancedPricing::COL_TIER_PRICE_WEBSITE => 'ap.website_id',
474+
ImportAdvancedPricing::VALUE_ALL_GROUPS => 'ap.all_groups',
475+
ImportAdvancedPricing::COL_TIER_PRICE_CUSTOMER_GROUP => 'ap.customer_group_id',
476+
ImportAdvancedPricing::COL_TIER_PRICE_QTY => 'ap.qty',
477+
ImportAdvancedPricing::COL_TIER_PRICE => 'ap.value',
478+
ImportAdvancedPricing::COL_TIER_PRICE_PERCENTAGE_VALUE => 'ap.percentage_value',
479+
'product_link_id' => 'ap.' .$productEntityLinkField,
480+
];
481+
if ($exportFilter) {
482+
if (array_key_exists('tier_price', $exportFilter)) {
483+
if (!empty($exportFilter['tier_price'][0])) {
484+
$priceFromFilter = $exportFilter['tier_price'][0];
485+
}
486+
if (!empty($exportFilter['tier_price'][1])) {
487+
$priceToFilter = $exportFilter['tier_price'][1];
488+
}
489+
}
490+
}
491+
492+
$select = $this->_connection->select()
493+
->from(
494+
['ap' => $this->_resource->getTableName($pricesTable)],
495+
$selectFields
496+
)
497+
->where(
498+
'ap.'.$productEntityLinkField.' IN (?)',
499+
$productIds
500+
);
501+
502+
if ($priceFromFilter !== null) {
503+
$select->where('ap.value >= ?', $priceFromFilter);
504+
}
505+
if ($priceToFilter !== null) {
506+
$select->where('ap.value <= ?', $priceToFilter);
507+
}
508+
if ($priceFromFilter || $priceToFilter) {
509+
$select->orWhere('ap.percentage_value IS NOT NULL');
510+
}
511+
512+
return $this->_connection->fetchAll($select);
513+
}
514+
340515
/**
341516
* Get tier prices.
342517
*
@@ -345,6 +520,8 @@ private function tierPriceTypeValue($tierPricePercentage)
345520
* @return array|bool
346521
* @SuppressWarnings(PHPMD.NPathComplexity)
347522
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
523+
* @deprecated
524+
* @see fetchTierPrices
348525
*/
349526
protected function getTierPrices(array $listSku, $table)
350527
{
@@ -413,40 +590,51 @@ protected function getTierPrices(array $listSku, $table)
413590
}
414591

415592
/**
416-
* Get Website code
593+
* Get Website code.
417594
*
418595
* @param int $websiteId
596+
*
419597
* @return string
420598
*/
421-
protected function _getWebsiteCode($websiteId)
599+
protected function _getWebsiteCode(int $websiteId): string
422600
{
423-
$storeName = ($websiteId == 0)
424-
? ImportAdvancedPricing::VALUE_ALL_WEBSITES
425-
: $this->_storeManager->getWebsite($websiteId)->getCode();
426-
$currencyCode = '';
427-
if ($websiteId == 0) {
428-
$currencyCode = $this->_storeManager->getWebsite($websiteId)->getBaseCurrencyCode();
429-
}
430-
if ($storeName && $currencyCode) {
431-
return $storeName . ' [' . $currencyCode . ']';
432-
} else {
433-
return $storeName;
601+
if (!array_key_exists($websiteId, $this->websiteCodesMap)) {
602+
$storeName = ($websiteId == 0)
603+
? ImportAdvancedPricing::VALUE_ALL_WEBSITES
604+
: $this->_storeManager->getWebsite($websiteId)->getCode();
605+
$currencyCode = '';
606+
if ($websiteId == 0) {
607+
$currencyCode = $this->_storeManager->getWebsite($websiteId)
608+
->getBaseCurrencyCode();
609+
}
610+
611+
if ($storeName && $currencyCode) {
612+
$code = $storeName.' ['.$currencyCode.']';
613+
} else {
614+
$code = $storeName;
615+
}
616+
$this->websiteCodesMap[$websiteId] = $code;
434617
}
618+
619+
return $this->websiteCodesMap[$websiteId];
435620
}
436621

437622
/**
438-
* Get Customer Group By Id
623+
* Get Customer Group By Id.
624+
*
625+
* @param int $groupId
626+
* @param int $allGroups
439627
*
440-
* @param int $customerGroupId
441-
* @param null $allGroups
442628
* @return string
443629
*/
444-
protected function _getCustomerGroupById($customerGroupId, $allGroups = null)
445-
{
446-
if ($allGroups) {
630+
protected function _getCustomerGroupById(
631+
int $groupId,
632+
int $allGroups = 0
633+
): string {
634+
if ($allGroups !== 0) {
447635
return ImportAdvancedPricing::VALUE_ALL_GROUPS;
448636
} else {
449-
return $this->_groupRepository->getById($customerGroupId)->getCode();
637+
return $this->_groupRepository->getById($groupId)->getCode();
450638
}
451639
}
452640

0 commit comments

Comments
 (0)