製品コレクション内の別の属性で製品コレクションをフィルタリング(例: 'attribX'、array( 'gt' => 'attrib-Y')


7

このような製品コレクションを使用する場合:

$_productCollection= Mage::getModel('catalog/product')->getCollection()
                    ->addAttributeToSelect('*')
                    ->addAttributeToFilter('special_price', array('neq'=>''));

別の属性に関連する属性でaddAttributeToFilterを使用することは可能ですか?例:価格よりも高いspecial_priceを次のようにフィルタリングできますか

$_productCollection= Mage::getModel('catalog/product')->getCollection()
                    ->addAttributeToSelect('*')
                    ->addAttributeToFilter('special_price', array('gt'=>'price'));

回答:


4

あなたはこれを使ってこれを達成できると思いますaddExpressionAttributeToSelect。これについてはクラスMage_Eav_Model_Entity_Collection_Abstractを参照してください。あなたはこのようなことを試すことができます:

$_productCollection= Mage::getModel('catalog/product')->getCollection()
    ->addAttributeToSelect('*')
    ->addExpressionAttributeToSelect('difference', '(IF ({{special_price}} > {{price}} , 1, 0))', array('special_price', 'price'));

これによりdifference、特別価格が価格よりも大きい場合に、値が1のselectに名前が付けられた新しい「列」が追加されます。これで、その列でフィルターするだけです。

$_productCollection->getSelect()->having('difference = ?', 1);

優れたシンプルなソリューションですが、最適なクエリパフォーマンスが必要な場合は、回避することをお勧めしますHAVING
Fabian Schmengler

それ以外の方法では機能しないと思います
マリウス

私の解決策は簡単ではありませんが、うまくいくようです。
Fabian Schmengler、2016年

1

Zend_Db_Expr値の代わりに生のSQLを使用できます。ただし、商品コレクションでは、フラット商品インデックスが有効になっているとクエリが異なるため、注意が必要です。

EAV(フラットインデックスがオフまたは管理領域)

ここで、2番目の属性のフィルターも追加する必要があります。選択する属性は2番目のクエリで読み込まれ、それ以外の場合はアクセスできないためです。常に真実であるものを選択し、私は「notnull」を選びました。結合された属性テーブルは、 "at_" +属性コードで参照できます。

$_productCollection
    ->addAttributeToFilter('price', ['notnull' => true])
    ->addAttributeToFilter(
        'special_price',
        ['lt' => new Zend_Db_Expr('at_price.value')]
    );

フラットインデックスの使用

フラットインデックスを使用すると、フラットインデックスに含まれている任意の属性に直接アクセスできます(「製品リストで使用」など)。

$_productCollection->addAttributeToFilter(
    'special_price',
    ['lt' => new Zend_Db_Expr('price')]
);

ユニバーサルソリューション

使用addExpressionAttributeToSelect()@Mariusにより示唆されるように、私たちは式の中で使用されるすべての属性がダミーフィルタ(両方とも同じようにうまく単に回避策が、作業している)を追加することなく、利用できることを確認することができます。次に、以下に応じて、異なる式を使用するだけですisEnabledFlat()

$priceExpression = $_productCollection()->isEnabledFlat()
    ? new Zend_Db_Expr('price')
    : new Zend_Db_Expr('at_price.value');
$_productCollection
    ->addExpressionAttributeToSelect('difference', '(IF ({{special_price}} > {{price}} , 1, 0))', array('special_price', 'price'));
    ->addAttributeToFilter(
        'special_price',
        ['lt' => $priceExpression]
    );

値が計算される前に実行されるdifferenceため、実際にはフィルターで使用しないことに注意してくださいWHERE。しかしこれは、MySQLがHAVING最後に実行されるを使用するよりもクエリを最適化できることも意味します。

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.