Как отфильтровать коллекцию продуктов по значениям параметров администратора атрибута?


В настоящее время я разрабатываю конфигуратор продукта. Я отправляю форму, которая отправляет значения параметров администратора моих пользовательских атрибутов по почте в действие контроллера. Если я использую ярлыки атрибутов текущего магазина, все работает нормально, коллекция продуктов фильтруется правильно, и возвращается простой продукт, связанный с настраиваемым продуктом. К сожалению, я использую значения администратора для генерации форм и URL-адресов, потому что шведский магазин по умолчанию значения содержат слишком много специальных символов.

Итак, мой вопрос: как мне получить правильный продукт из моей коллекции при использовании значений параметров администратора или, более конкретно, как мне получить идентификатор значения параметра администратора, например, используя это для значений магазина по умолчанию:

$id = Mage::getResourceModel('catalog/product')
                                    ->getAttribute($key)
                                    ->getSource()
                                    ->getOptionId($value); 

Я уже пробовал фильтровать с помощью addStoreFilter(0), но это тоже не сработало. Я уже читал, что это может иметь какое-то отношение к плоским таблицам, используемым в магазине по умолчанию, но не для администратора, но я скорее у меня нет опыта работы с Magento, поэтому я не совсем понимаю разницу в использовании плоских таблиц и что это на самом деле означает.

Вот мой последний вопрос, касающийся фильтрации для справки: addFieldToFilter не возвращает правильный продукт для выбранных значений атрибутов

Вот моя функция getProduct():

public function getProduct($attributes)
    {

        Mage::Log($attributes);

        $productModel = Mage::getModel('catalog/product');

        //Get Product Collection
        $collection = $productModel->getCollection()


        //Filter for Selected Product
        $collection->addAttributeToSelect('status');
        $collection->addAttributeToSelect('doorconfig_enable');
        $collection->addAttributeToFilter('doorconfig_enable',array('eq' => 1));

        foreach ($attributes as $key => $value) 
        {
            $collection->addAttributeToSelect($key);

            $id = Mage::getResourceModel('catalog/product')
                                    ->getAttribute($key)
                                    ->getSource()
                                    ->getOptionId($value);

            $collection->addAttributeToFilter($key,
                array(
                        'eq' => $id
                     )
            );

        }

        $selection = $collection->getSelect()->__toString();

        Mage::Log($selection);

        Mage::log($collection->getSize(),null,'custom.log');

        $product = $collection->getFirstItem();

        return $product;

    }
Author: Community, 2013-07-24

1 answers

Как и все в Magento, ответ находится в источнике - все, что вам нужно сделать, это начать копать (или перейти к концу этого поста).

Сначала найдите класс для источника атрибута

$source = Mage::getResourceModel('catalog/product')
->getAttribute('color')
->getSource();        
var_dump(get_class($source));
exit;

В современных версиях Magento это должно указывать на класс Mage_Eav_Model_Entity_Attribute_Source_Table, который находится по адресу

#File: app/code/core/Mage/Eav/Model/Entity/Attribute/Source/Table.php
class Mage_Eav_Model_Entity_Attribute_Source_Table extends Mage_Eav_Model_Entity_Attribute_Source_Abstract
{
    //...
}

Далее мы будем искать определение метода getOptionId для этого класса и/или его родительских классов. Мы найдем его в классе Mage_Eav_Model_Entity_Attribute_Source_Abstract

#File: app/code/core/Mage/Eav/Model/Entity/Attribute/Source/Abstract.php
public function getOptionId($value)
{
    foreach ($this->getAllOptions() as $option) {
        if (strcasecmp($option['label'], $value)==0 || $option['value'] == $value) {
            return $option['value'];
        }
    }
    return null;
}

Изучение этого метода, мы можем увидеть, работает ли foreach по списку опций из метода getAllOptions. Итак, давайте рассмотрим определение этого метода.

#File: app/code/core/Mage/Eav/Model/Entity/Attribute/Source/Table.php
public function getAllOptions($withEmpty = true, $defaultValues = false)
{
    $storeId = $this->getAttribute()->getStoreId();
    if (!is_array($this->_options)) {
        $this->_options = array();
    }
    if (!is_array($this->_optionsDefault)) {
        $this->_optionsDefault = array();
    }
    if (!isset($this->_options[$storeId])) {
        $collection = Mage::getResourceModel('eav/entity_attribute_option_collection')
            ->setPositionOrder('asc')
            ->setAttributeFilter($this->getAttribute()->getId())
            ->setStoreFilter($this->getAttribute()->getStoreId())
            ->load();
        $this->_options[$storeId]        = $collection->toOptionArray();
        $this->_optionsDefault[$storeId] = $collection->toOptionArray('default_value');
    }
    $options = ($defaultValues ? $this->_optionsDefault[$storeId] : $this->_options[$storeId]);
    if ($withEmpty) {
        array_unshift($options, array('label' => '', 'value' => ''));
    }

    return $options;
}

Ах, ха! Теперь мы кое-что выяснили. Похоже, это метод, который загружает всю информацию о параметрах. В частности, нас интересует

$storeId = $this->getAttribute()->getStoreId();

Итак, Magento получает идентификатор магазина для параметров загрузки из атрибута . Это означает, что вы должны быть в состоянии сделать что-то вроде следующего (заменив color и red своими собственными переменные, конечно)

    //get the attribute
    $attribute = Mage::getResourceModel('catalog/product')
    ->getAttribute('color');

    //set the store id on the attribute
    $attribute->setStoreId(Mage_Core_Model_App::ADMIN_STORE_ID);

    //get the source
    $source = $attribute->getSource();

    //get the id
    $id = $source->getOptionId('red');
 4
Author: Alan Storm, 2013-08-06 17:19:35