Domanda

sto facendo quanto segue:

$productCollection = Mage::getModel('catalog/product')
    ->getCollection();

$productCollection
    ->addAttributeToFilter('my_attribute', 1);

my_attribute non è nelle tabelle piatte, ma le tabelle piatte sono abilitati.

Continuo a ricevere la collezione completa.

Il motivo sembra essere in \Mage_Catalog_Model_Resource_Product_Collection::addAttributeToSelect:

$columns = $this->getEntity()->getAttributeForSelect($attributeCode);

Non $this->getEntity() è un'istanza di Mage_Catalog_Model_Resource_Product_Flat che recupera i campi piatti -. E se non viene trovato, appena restituisce null

Che cosa è un modo pulito per aggiungere un attributo non piatta per il filtro di raccolta?

Nel mio caso non rileva, per aggiungere l'attributo al tavolo piano.

È stato utile?

Soluzione

Si potrebbe unirsi al tavolo da soli necessaria.

$productCollection = Mage::getModel('catalog/product')
->getCollection();

$table = Mage::getSingleton('eav/config')->getAttribute('catalog_product', 'my_attribute')->getBackend()->getTable();
$attributeId = Mage::getSingleton('eav/config')->getAttribute('catalog_product', 'my_attribute')->getAttributeId();

$productCollection->getSelect()->join(array('attributeTable' => $table), 'e.entity_id = attributeTable.entity_id', array('my_attribute' => 'attributeTable.value'))
                            ->where("attributeTable.attribute_id = ?", $attributeId)
                            ->where("attributeTable.value = ?", 1);

Si potrebbe desiderare di unirsi per STORE_ID, anche.

Altri suggerimenti

Un hack (CE 1.6.2.0+) è per passare la condizione come un array e credere o no questo funziona come previsto:

$collection->addFieldToFilter(array(array('attribute' => 'my_attribute', 'eq' => 1)));

La ragione la risposta di ColinM funziona è dovuto al codice nel metodo di app/code/core/Mage/Catalog/Model/Resource/Product/Collection.php di addAttributeToFilter. Se si utilizza questo formato array, non chiama addAttributeToSelect. In modalità piatta, addAttributeToSelect riuscita automaticamente se l'attributo non è presente nella tabella piatta.

(qui di seguito è un re-hash della mia risposta su https://stackoverflow.com/questions/6271284/can-i-add-other-attributes-to-magentos-flat-product-catalog-table/17021620 - io non sono sicuro di ciò che l'etichetta è per questo, ma so che avrei trovato utile)

I desiderava una soluzione "pulita" per la raccolta piatto selezione di modo e filtrando su attributi non piane, che:

  • non richiede l'attributo di avere impostazioni specifiche in admin (che potrebbe essere aggiunto da un utente, o nascosto sul front-end)
  • funziona sia piatta e modalità non-flat

ho usato la raccolta del prodotto associato, ma questo vale per qualsiasi raccolta EAV.

Codice mancanza:

$_product = Mage::getModel('catalog/product')->loadByAttribute( 'sku', 'ABC123' );
$coll = $_product->getTypeInstance()->getAssociatedProductCollection()
    ->addAttributeToSelect( 'my_custom_attribute' )
    ->addAttributeToFilter( 'my_custom_attribute', 3 )
;

Nel piatto, il codice precedente non riesce automaticamente per selezionare o filtro sul attributo se per caso non è nella tavola piana.

In aggiunta alla select:

$_product = Mage::getModel('catalog/product')->loadByAttribute( 'sku', 'ABC123' );
$coll = $_product->getTypeInstance()->getAssociatedProductCollection()
    ->joinAttribute( 'my_custom_attribute', 'catalog_product/my_custom_attribute', 'entity_id', null, 'left' )
    ->addAttributeToSelect( 'my_custom_attribute' )
;

Il metodo joinAttribute aggiunge una join alla query per l'attributo specifica richiesta. Ancora funziona quando l'attributo è già nella tavola piana, ma sarà leggermente meno efficiente rispetto puramente utilizzando la tabella piatta.

Ho usato un left unirsi lì, per garantire che essa recupera i prodotti se my_custom_attribute non è impostato su tali prodotti. Cambiamento che per inner se siete interessati solo a righe in cui è impostato my_custom_attribute.

Aggiunta al filtro (secondo ColinM sopra):

$_product = Mage::getModel('catalog/product')->loadByAttribute( 'sku', 'ABC123' );
$coll = $_product->getTypeInstance()->getAssociatedProductCollection()
    ->addAttributeToFilter( array( array( 'attribute' => 'my_custom_attribute', 'eq' => 3 ) ) )
;

Il codice qui sopra aggiungerlo al selezionare così come obbedendo il filtro.

(testato in CE 1.6.2.0)

Nel modulo Mage_Rss hanno usato l'un hacky-metodo per disattivare le tabelle piatte. Usano il fatto, che le tabelle piatti sono sempre fuori nel negozio di amministrazione e quindi basta emulare il negozio di amministrazione.

class Mage_Rss_Helper_Data {

[...]

/**
 * Disable using of flat catalog and/or product model to prevent limiting results to single store. Probably won't
 * work inside a controller.
 *
 * @return null
 */
public function disableFlat()
{
    /* @var $flatHelper Mage_Catalog_Helper_Product_Flat */
    $flatHelper = Mage::helper('catalog/product_flat');
    if ($flatHelper->isEnabled()) {
        /* @var $emulationModel Mage_Core_Model_App_Emulation */
        $emulationModel = Mage::getModel('core/app_emulation');
        // Emulate admin environment to disable using flat model - otherwise we won't get global stats
        // for all stores
        $emulationModel->startEnvironmentEmulation(0, Mage_Core_Model_App_Area::AREA_ADMINHTML);
    }
}

Dopo aver avviato l'emulazione si dovrebbe resettare con emulationModel->stopEnvironmentEmulation()

quando si crea l'attributo che dovrebbe essere a livello globale e filtrabile. In questo modo sarà utilizzabile nella navigazione layared. Inoltre richiederà l'attributo di essere una discesa o selezione multipla. Io personalmente consiglio di non modificare i file di base per soddisfare le vostre esigenze in questo caso

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a magento.stackexchange
scroll top