diff --git a/vendor/magento/module-catalog-graph-ql/DataProvider/Product/LayeredNavigation/AttributeOptionProvider.php b/vendor/magento/module-catalog-graph-ql/DataProvider/Product/LayeredNavigation/AttributeOptionProvider.php index 576281861d3..65620b667bb 100644 --- a/vendor/magento/module-catalog-graph-ql/DataProvider/Product/LayeredNavigation/AttributeOptionProvider.php +++ b/vendor/magento/module-catalog-graph-ql/DataProvider/Product/LayeredNavigation/AttributeOptionProvider.php @@ -8,6 +8,8 @@ declare(strict_types=1); namespace Magento\CatalogGraphQl\DataProvider\Product\LayeredNavigation; use Magento\Framework\App\ResourceConnection; +use Magento\Framework\DB\Select; +use Magento\Store\Model\Store; /** * Fetch product attribute option data including attribute info @@ -50,16 +52,18 @@ class AttributeOptionProvider * Get option data. Return list of attributes with option data * * @param array $optionIds + * @param int|null $storeId * @param array $attributeCodes * @return array * @throws \Zend_Db_Statement_Exception */ - public function getOptions(array $optionIds, array $attributeCodes = [], $storeId): array + public function getOptions(array $optionIds, ?int $storeId, array $attributeCodes = []): array { if (!$optionIds) { return []; } + $storeId = $storeId ?: Store::DEFAULT_STORE_ID; $connection = $this->resourceConnection->getConnection(); $select = $connection->select() ->from( @@ -87,10 +91,24 @@ class AttributeOptionProvider ['option_value' => $this->resourceConnection->getTableName('eav_attribute_option_value')], 'options.option_id = option_value.option_id', [ - 'option_label' => 'option_value.value', 'option_id' => 'option_value.option_id', 'option_store_id' => 'option_value.store_id' ] + )->joinLeft( + ['option_value_store' => $this->resourceConnection->getTableName('eav_attribute_option_value')], + "options.option_id = option_value_store.option_id AND option_value_store.store_id = {$storeId}", + [ + 'option_label' => $connection->getCheckSql( + 'option_value_store.value_id > 0', + 'option_value_store.value', + 'option_value.value' + ) + ] + )->where( + 'a.attribute_id = options.attribute_id AND option_value.store_id = ?', + Store::DEFAULT_STORE_ID + )->order( + 'options.sort_order ' . Select::SQL_ASC ); $select->where('option_value.option_id IN (?)', $optionIds); @@ -109,11 +127,11 @@ class AttributeOptionProvider /** * Format result * - * @param \Magento\Framework\DB\Select $select + * @param Select $select * @return array * @throws \Zend_Db_Statement_Exception */ - private function formatResult(\Magento\Framework\DB\Select $select, $storeId): array + private function formatResult(Select $select, $storeId): array { $statement = $this->resourceConnection->getConnection()->query($select); @@ -141,8 +159,10 @@ class AttributeOptionProvider 'options' => [], ]; } - - $result[$option['attribute_code']]['options'][$option['option_id']] = $option_Text; + + if (!empty($option['option_id'])) { + $result[$option['attribute_code']]['options'][$option['option_id']] = $option_Text; + } } return $result; diff --git a/vendor/magento/module-catalog-graph-ql/DataProvider/Product/LayeredNavigation/Builder/Attribute.php b/vendor/magento/module-catalog-graph-ql/DataProvider/Product/LayeredNavigation/Builder/Attribute.php index e550de9cb03..8361fbb0bf9 100644 --- a/vendor/magento/module-catalog-graph-ql/DataProvider/Product/LayeredNavigation/Builder/Attribute.php +++ b/vendor/magento/module-catalog-graph-ql/DataProvider/Product/LayeredNavigation/Builder/Attribute.php @@ -86,12 +86,12 @@ class Attribute implements LayerBuilderInterface $attribute['attribute_code'] ?? $bucketName ); - foreach ($bucket->getValues() as $value) { - $metrics = $value->getMetrics(); + $options = $this->getSortedOptions($bucket,$attribute['options'] ?: []); + foreach ($options as $option) { $result[$bucketName]['options'][] = $this->layerFormatter->buildItem( - $attribute['options'][$metrics['value']] ?? $metrics['value'], - $metrics['value'], - $metrics['count'] + $option['label'], + $option['value'], + $option['count'] ); } } @@ -133,10 +133,11 @@ class Attribute implements LayerBuilderInterface * Get list of attributes with options * * @param AggregationInterface $aggregation + * @param int|null $storeId * @return array * @throws \Zend_Db_Statement_Exception */ - private function getAttributeOptions(AggregationInterface $aggregation, $storeId): array + private function getAttributeOptions(AggregationInterface $aggregation, ?int $storeId): array { $attributeOptionIds = []; $attributes = []; @@ -154,6 +155,39 @@ class Attribute implements LayerBuilderInterface return []; } - return $this->attributeOptionProvider->getOptions(\array_merge(...$attributeOptionIds), $attributes,$storeId); + return $this->attributeOptionProvider->getOptions(\array_merge(...$attributeOptionIds), $storeId, $attributes); + } + + /** + * Get sorted options + * + * @param BucketInterface $bucket + * @param array $optionLabels + * @return array + */ + private function getSortedOptions(BucketInterface $bucket, array $optionLabels): array + { + /** + * Option labels array has been sorted + */ + $options = $optionLabels; + foreach ($bucket->getValues() as $value) { + $metrics = $value->getMetrics(); + $optionValue = $metrics['value']; + $optionLabel = $optionLabels[$optionValue] ?? $optionValue; + $options[$optionValue] = $metrics + ['label' => $optionLabel]; + } + + /** + * Delete options without bucket values + */ + foreach ($options as $optionId => $option) { + if (!is_array($options[$optionId])) { + unset($options[$optionId]); + } + } + + return array_values($options); } } +