অ্যাডফিল্টার বনাম অ্যাডফিল্ডটোফিল্টার


19

ফিল্টারিংয়ের জন্য ম্যাজেন্টো সংগ্রহের দুটি পদ্ধতি রয়েছে:

1. Varien_Data_Collection_Db::addFieldToFilter
2. Varien_Data_Collection::addFilter

দেখে মনে হচ্ছে যে উভয় পদ্ধতিই শর্তটি যুক্ত করে Zend_Db_Select। এবং কি সুবিধা addFilterনিয়ে আসে? এর পরিবর্তে আমি কখন এটি ব্যবহার করব addFieldToFilter?

উত্তর:


49

ঠিক আছে, আসুন তাদের পরীক্ষা করা যাক। প্রথম পার্থক্যটি হ'ল addFilter()আরও জেনেরিক এবং ডাটাবেস নির্দিষ্ট নয়। এটি Varien_Directory_Collectionফাইলের নামে ফিল্টার করতেও ব্যবহৃত হয় । তবে এই উত্তরের জন্য আমি ফোকাস করতে যাচ্ছি Varien_Data_Collection_Db

তাদের পদ্ধতির আলাদা স্বাক্ষর রয়েছে, যেখানে addFilterকম নমনীয় বলে মনে হচ্ছে, তবে আপনি দেখতে পাবেন এর এর সুবিধাগুলিও রয়েছে:

1. addFieldToFilter ()

/**
 * Add field filter to collection
 *
 * @see self::_getConditionSql for $condition
 *
 * @param   string|array $field
 * @param   null|string|array $condition
 *
 * @return  Mage_Eav_Model_Entity_Collection_Abstract
 */
public function addFieldToFilter($field, $condition = null)

পরামিতি

অ্যাডফিল্ডটোফিল্টার () শর্তের অ্যারে সহ একটি ক্ষেত্রের অ্যারে বা একক শর্ত সহ একটি ক্ষেত্র নিতে পারে:

  • addFieldToFilter('field', 'value')

    ফলাফল স্বরূপ: field=value

  • addFieldToFilter(['field1', 'field2'], ['value1', 'value2']);

    ফলাফল স্বরূপ: field1=value1 OR field2=value2

প্রতিটি শর্ত হতে পারে:

  • একটি একক স্কেলারের মান (মত 'value1'এবং 'value2'উপরে)
  • আকারে একটি অ্যারে [ operator => value ]
  • একটি Zend_Db_Exprবস্তু
  • "OR" এর সাথে একত্রিত হওয়া শর্তগুলির একটি অ্যারে (হ্যাঁ, এটি পুনরাবৃত্তিযোগ্য)

এটি, বিশেষত "অপারেটর => মান" বাক্যটি কোডটিতে নথিবদ্ধ হয় Varien_Db_Adapter_Pdo_Mysql::prepareSqlCondition()- এটি মনে রাখবেন, আমি তাদের প্রায়শই সন্ধান করি:

 * If $condition integer or string - exact value will be filtered ('eq' condition)
 *
 * If $condition is array - one of the following structures is expected:
 * - array("from" => $fromValue, "to" => $toValue)
 * - array("eq" => $equalValue)
 * - array("neq" => $notEqualValue)
 * - array("like" => $likeValue)
 * - array("in" => array($inValues))
 * - array("nin" => array($notInValues))
 * - array("notnull" => $valueIsNotNull)
 * - array("null" => $valueIsNull)
 * - array("moreq" => $moreOrEqualValue)
 * - array("gt" => $greaterValue)
 * - array("lt" => $lessValue)
 * - array("gteq" => $greaterOrEqualValue)
 * - array("lteq" => $lessOrEqualValue)
 * - array("finset" => $valueInSet)
 * - array("regexp" => $regularExpression)
 * - array("seq" => $stringValue)
 * - array("sneq" => $stringValue)
 *
 * If non matched - sequential array is expected and OR conditions
 * will be built using above mentioned structure

from/ toঅপারেটরে অতিরিক্ত অনিবন্ধিত বৈশিষ্ট্য রয়েছে :

  • সঙ্গে এবং মান তারিখ হিসাবে বিশ্লেষণ করা হবে। তারা যে কোনও ফর্ম হতে পারে যা গ্রহণ করে['from' => $dateFrom, 'to' => $dateTo, 'date' => true]$dateFrom$dateToVarien_Date::formatDate()
  • আপনার যদি তারিখ বিশ্লেষণ বৈশিষ্ট্যটি প্রয়োজন তবে কেবল একটি <=বা এর সাথে তুলনা করার জন্য >=, আপনি হয় বাদ দিতে পারেন 'from'বা 'to'
  • 'datetime' => trueখুব বেশি কাজ করার এবং সময়টি কেবলমাত্র দিনটিকেই অন্তর্ভুক্ত করার কথা ছিল না, তবে ভারিয়ান_ডিবি_এডাপ্টার_পডো_মাইএসকিএল :: _ প্রস্তুতকার্য স্কেলডেটকন্ডিশন () (অনুপস্থিত $includeTimestampপরামিতি) যা কাজটিকেdatetime একইভাবে করে তোলে dateউভয় সময় অন্তর্ভুক্ত। তাই আপনি যদি শুধুমাত্র তারিখ অনুসারে তুলনা করতে হবে, যোগ 00:00:00করার fromতারিখ এবং 23:59:59করতে toতারিখ।

ফিল্ড ম্যাপিং

পদ্ধতিটি ফিল্ড ম্যাপিং ব্যবহার করে। ফিল্ড ম্যাপিংগুলি উপন্যাসের ক্ষেত্রের নামগুলি তৈরি করতে কংক্রিট সংগ্রহের ক্লাসে সংজ্ঞায়িত করা যেতে পারে। পণ্য সংগ্রহের একটি উদাহরণ এখানে:

protected $_map = array('fields' => array(
    'price'         => 'price_index.price',
    'final_price'   => 'price_index.final_price',
    'min_price'     => 'price_index.min_price',
    'max_price'     => 'price_index.max_price',
    'tier_price'    => 'price_index.tier_price',
    'special_price' => 'price_index.special_price',
));

2. অ্যাড ফিল্টার ()

/**
 * Add collection filter
 *s
 * @param string $field
 * @param string $value
 * @param string $type and|or|string
 */
public function addFilter($field, $value, $type = 'and')

পরামিতি

addFilter()কেবলমাত্র একটি একক ক্ষেত্রকে একটি একক মান এবং একটি ধরণের দ্বারা ফিল্টার করার অনুমতি দেয় । $typeযে কোনও হতে পারে:

  • "এবং" (ডিফল্ট) - AND $field=$valueযেখানে বিধি যুক্ত করেছে (অবশ্যই যথাযথ উদ্ধৃতি সহ)
  • "বা" - "OR $field=$valueযেখানে বিধি জুড়ে (ডাইটো)
  • "স্ট্রিং" - AND $valueযেখানে বিধি যুক্ত করে (অর্থাত্ an মানটি একটি নির্বিচারে এসকিউএল এক্সপ্রেশন হতে পারে)
  • "সর্বজনীন" - ফিল্ড ম্যাপিং এবং এর _getConditionSql()অনুরূপ ব্যবহার করে addFieldToFilter()। এটি এটি প্রায় হিসাবে শক্তিশালী করে তোলে, এটি ওআরের সাথে মিলিত বিভিন্ন ক্ষেত্রের জন্য একাধিক ফিল্টার যুক্ত করার বৈশিষ্ট্যটি কেবল হারিয়েছে।

এগুলিতে Varien_Data_Collection_Db::_renderFilters()কীভাবে প্রক্রিয়া করা হয় তা আপনি দেখতে পাবেন।

extensibility

সেখানে একটি গুরুত্বপূর্ণ পার্থক্য, যার জন্য একটি সুবিধা হল addFilter()। এটি প্রয়োগ করার জন্য ফিল্টারগুলি সংগ্রহ করে $this->_filters()এবং Zend_Db_Selectসংগ্রহটি লোড করার ঠিক আগে এগুলি ক্যোয়ারী অবজেক্টে যুক্ত করে। addFieldToFilter()অন্যদিকে তাত্ক্ষণিকভাবে ক্যোয়ারী অবজেক্টটিকে ম্যানিপুলেট করে।

এটি আপনাকে ইতিমধ্যে যুক্ত করা ফিল্টারগুলি পরিচালনা করতে বা সরাতে দেয়। ভ্যারিয়ান সংগ্রহের এটির জন্য কোনও ইন্টারফেস নেই, আপনাকে এটি আপনার কাস্টম সংগ্রহে প্রয়োগ করতে হবে। একটি হুক পদ্ধতি রয়েছে _renderFiltersBefore()যা আপনি ওভাররাইড করতে পারেন।


আমি একটা প্রশ্ন আমরা ব্যবহার করতে addFilterদিয়ে attributes?
মুরতুজা জাবাওয়ালা

@ মুরতুজাবাবুওয়ালা না, এটি EAV বৈশিষ্ট্যের জন্য ব্যবহার করা যাবে না
ফ্যাবিয়ান শেমংলার

এই উত্তরটির জন্য আপনাকে ধন্যবাদ ফ্যাবিয়ান, আমি আপনার ওয়েবসাইটের পোস্টটিও এ সম্পর্কে উপভোগ করেছি তবে অ্যাডফিল্টারটিতে কী মান $ ফিল্ড ধরে রাখতে পারে? আমি মডিউলটি যে বিভাগে চলছে সেগুলি কেবলমাত্র ফিল্টার করতে অ্যাড ফিল্টার ফাংশনটি ব্যবহার করার চেষ্টা করছি
জন

ক্যাটাগরির বৈশিষ্ট্যগুলি নয় তবে পৃথক টেবিলের পণ্যগুলির সাথে সম্পর্কিত হওয়ায় আফাইক সম্ভব নয় possible আপনাকে আমার মাথার উপরে সমাধান দিতে পারে না, দুঃখিত
ফ্যাবিয়ান শেমংলার

প্রতিক্রিয়া জানাতে ধন্যবাদ, কোনও উদ্বেগ নেই, আমি যদি কোনও উপায় খুঁজে পাই তবে আমি আমার সমাধানটি আপডেট করব
জন

2

ম্যাগন্টো সংগ্রহের বেলো পৃথকীকরণের দুটি পদ্ধতি রয়েছে

  1. Varien_Data_Collection_Db :: addFieldToFilter

addFieldToFilter ($ ক্ষেত্র, $ শর্ত = নাল)

প্রথম প্যারামিটার addFieldToFilterহল সেই বৈশিষ্ট্যটি যা আপনি দ্বারা ফিল্টার করতে চান। দ্বিতীয়টি হ'ল আপনি যে মানটি সন্ধান করছেন তা। এখানে আমরা skuমানটির জন্য একটি ফিল্টার যুক্ত করছি n2610

আপনি যে ফিল্টারিং করতে চান তা নির্দিষ্ট করতে দ্বিতীয় প্যারামিটারও ব্যবহার করা যেতে পারে। এখানেই জিনিসগুলি কিছুটা জটিল হয়ে ওঠে এবং আরও কিছুটা গভীরতার সাথে worthোকা যায়।

সুতরাং ডিফল্টরূপে, নিম্নলিখিত

$collection_of_products->addFieldToFilter('sku','n2610'); 

(মূলত) এর সমতুল্য

WHERE sku = "n2610"

নিজের জন্য একটু দেখে যাও. নিম্নলিখিত চলমান

public function testAction()
{
    var_dump(
    (string) 
    Mage::getModel('catalog/product')
    ->getCollection()
    ->addFieldToFilter('sku','n2610')
    ->getSelect());
}

ফলন হবে

SELECT `e`.* FROM `catalog_product_entity` AS `e` WHERE (e.sku = 'n2610')'

মনে রাখবেন, আপনি যদি EAV বৈশিষ্ট্যটি ব্যবহার করেন তবে এটি দ্রুত জটিল হয়ে উঠতে পারে। একটি বৈশিষ্ট্য যুক্ত করুন

var_dump(
(string) 
Mage::getModel('catalog/product')
->getCollection()
->addAttributeToSelect('*')
->addFieldToFilter('meta_title','my title')
->getSelect()
);

এবং ক্যোয়ারী চমকপ্রদ হয়ে ওঠে।

SELECT `e`.*, IF(_table_meta_title.value_id>0, _table_meta_title.value, _table_meta_title_default.value) AS `meta_title` 
FROM `catalog_product_entity` AS `e` 
INNER JOIN `catalog_product_entity_varchar` AS `_table_meta_title_default` 
    ON (_table_meta_title_default.entity_id = e.entity_id) AND (_table_meta_title_default.attribute_id='103') 
    AND _table_meta_title_default.store_id=0        
LEFT JOIN `catalog_product_entity_varchar` AS `_table_meta_title` 
    ON (_table_meta_title.entity_id = e.entity_id) AND (_table_meta_title.attribute_id='103') 
    AND (_table_meta_title.store_id='1') 
WHERE (IF(_table_meta_title.value_id>0, _table_meta_title.value, _table_meta_title_default.value) = 'my title')

বিন্দুটি বেলবোর করার জন্য নয়, তবে আপনি যদি সময়সীমাতে থাকেন তবে এসকিউএল সম্পর্কে খুব বেশি চিন্তা করার চেষ্টা করবেন না।

অন্যান্য তুলনা অপারেটরগণ আমি নিশ্চিত আপনি ভাবছেন যে "যদি আমি কোয়েরির সমতুল্য ব্যতীত অন্য কিছু চাই"? সমান নয়, এর চেয়ে কম, ইত্যাদি The অ্যাডফিল্ডটোফিল্টার পদ্ধতির দ্বিতীয় প্যারামিটারটি আপনি সেখানে coveredেকে রেখেছেন। এটি একটি বিকল্প বাক্য গঠন সমর্থন করে যেখানে স্ট্রিংয়ের পরিবর্তে, আপনি একটি একক উপাদান অ্যারে পাস করেন।

আপনি যে তুলনা করতে চান তা এই অ্যারের কীটি। এই কীটির সাথে সম্পর্কিত মানটি সেই মানটি যা আপনি ফিল্টার করতে চান। উপরের ফিল্টারটি আবার করুন, তবে এই স্পষ্ট বাক্য গঠন দিয়ে with

public function testAction()
{
    var_dump(
    (string) 
    Mage::getModel('catalog/product')
    ->getCollection()
    ->addFieldToFilter('sku',array('eq'=>'n2610'))
    ->getSelect()
    );          
}

আমাদের ফিল্টার কল করছে

addFieldToFilter('sku',array('eq'=>'n2610'))

আপনি দেখতে পাচ্ছেন, দ্বিতীয় প্যারামিটারটি পিএইচপি অ্যারে। এর কীটি একা, যা সমান। এই কীটির মান n2610, যা আমরা ফিল্টার করছি এমন মান।

ম্যাজেন্টোর এমন অনেকগুলি ইংরাজী ভাষা রয়েছে যেমন ফিল্টার যা শ্রোতাদের যে কোনও পুরানো পার্ল বিকাশকারীকে স্মরণ করার টিয়ার (এবং সম্ভবত ব্যথা) নিয়ে আসবে।

নীচে তালিকাভুক্ত সমস্ত ফিল্টার রয়েছে তাদের এসকিউএল সমতলের উদাহরণ সহ।

array("eq"=>'n2610')
WHERE (e.sku = 'n2610')

array("neq"=>'n2610')
WHERE (e.sku != 'n2610')

array("like"=>'n2610')
WHERE (e.sku like 'n2610')

array("nlike"=>'n2610')
WHERE (e.sku not like 'n2610')

array("is"=>'n2610')
WHERE (e.sku is 'n2610')

array("in"=>array('n2610'))
WHERE (e.sku in ('n2610'))

array("nin"=>array('n2610'))
WHERE (e.sku not in ('n2610'))

array("notnull"=>'n2610')
WHERE (e.sku is NOT NULL)

array("null"=>'n2610')
WHERE (e.sku is NULL)

array("gt"=>'n2610')
WHERE (e.sku > 'n2610')

array("lt"=>'n2610')
WHERE (e.sku < 'n2610')

array("gteq"=>'n2610')
WHERE (e.sku >= 'n2610')

array("moreq"=>'n2610') //a weird, second way to do greater than equal
WHERE (e.sku >= 'n2610')

array("lteq"=>'n2610')
WHERE (e.sku <= 'n2610')

array("finset"=>array('n2610'))
WHERE (find_in_set('n2610',e.sku))

array('from'=>'10','to'=>'20')
WHERE e.sku >= '10' and e.sku <= '20'

এগুলির বেশিরভাগ স্ব-বর্ণনামূলক, তবে কয়েকটি একটি বিশেষ কলআউট প্রাপ্য

ইন, নিন, সন্ধান_ইন_সেট ইন এবং নিন শর্তাদি আপনাকে মানগুলির একটি অ্যারেতে যেতে দেয়। অর্থাৎ, আপনার ফিল্টার অ্যারের মান অংশটি নিজেই অ্যারে হিসাবে অনুমোদিত।

array("in"=>array('n2610','ABC123')
WHERE (e.sku in ('n2610','ABC123'))

notnull, null মূল শব্দটি এনকিউএল এসকিউএল এর বেশিরভাগ স্বাদে বিশেষ। এটি সাধারণত স্ট্যান্ডার্ড সমতা (=) অপারেটরের সাথে দুর্দান্ত খেলবে না। আপনার ফিল্টার প্রকার হিসাবে নোটনাল বা নাল উল্লেখ করা আপনাকে কোনও নাল তুলনার জন্য সঠিক বাক্য গঠন দেবে এবং আপনি যে কোনও মান পাস করলে তা উপেক্ষা করবেন না

array("notnull"=>'n2610')
WHERE (e.sku is NOT NULL)

থেকে - ফিল্টার করতে এটি আরও একটি বিশেষ ফর্ম্যাট যা মানক নিয়মকে ভেঙে দেয়। একটি একক উপাদান অ্যারের পরিবর্তে, আপনি একটি দুটি উপাদান অ্যারে নির্দিষ্ট করুন। একটি উপাদান থেকে চাবি রয়েছে, অন্য উপাদানটির কী রয়েছে। কীগুলি নির্দেশিত হিসাবে, এই ফিল্টারটি আপনাকে চিহ্নগুলির চেয়ে বেশি এবং কম সম্পর্কে চিন্তা না করেই / থেকে একটি পরিসীমা নির্মান করতে দেয়

public function testAction
{
        var_dump(
        (string) 
        Mage::getModel('catalog/product')
        ->getCollection()
        ->addFieldToFilter('price',array('from'=>'10','to'=>'20'))
        ->getSelect()
        );                      
}

উপরের ফলন

WHERE (_table_price.value >= '10' and _table_price.value <= '20')'

এবং বা ওআর, বা এটি ওআর এবং এন্ড? অবশেষে, আমরা বুলিয়ান অপারেটরদের কাছে আসি। এটি বিরল মুহুর্ত যেখানে আমরা কেবল একটি বৈশিষ্ট্য দ্বারা ফিল্টার করছি। ভাগ্যক্রমে, ম্যাজেন্টোর সংগ্রহগুলি আমাদের কভার করেছে। সংখ্যক “এবং” কোয়েরি পেতে আপনি অ্যাডফিল্ডটোফিল্টারে একাধিক কল চেইন করতে পারেন।

function testAction()
{
        echo(
        (string) 
        Mage::getModel('catalog/product')
        ->getCollection()
        ->addFieldToFilter('sku',array('like'=>'a%'))
        ->addFieldToFilter('sku',array('like'=>'b%'))
        ->getSelect()
        );                                  
}

উপরের মত একাধিক কল এক সাথে শৃঙ্খলাবদ্ধ করে আমরা এমন একটি ক্লজ তৈরি করব যা নীচের মত দেখতে কিছু দেখায়

WHERE (e.sku like 'a%') AND (e.sku like 'b%')

আপনারা যারা সবেমাত্র আপনার হাত তুলেছেন তাদের কাছে হ্যাঁ, উপরের উদাহরণটি সর্বদা 0 টি রেকর্ড ফিরিয়ে আনবে। কোনও স্ক এবং দু'এই এবং এ-বি দিয়ে শুরু করা যাবে না। আমরা সম্ভবত এখানে যা চাই তা হল একটি ওআর ক্যোরি। এটি আমাদেরকে অ্যাডফিল্ডটোফিল্টারের দ্বিতীয় প্যারামিটারের বিভ্রান্তিকর দিকটিতে নিয়ে আসে।

আপনি যদি একটি ওআর ক্যোয়ারী তৈরি করতে চান তবে আপনাকে দ্বিতীয় প্যারামিটার হিসাবে ফিল্টার অ্যারের একটি অ্যারে পাস করতে হবে। আপনার পৃথক ফিল্টার অ্যারেগুলি ভেরিয়েবলগুলিতে নির্ধারণ করা ভাল বলে মনে করি

public function testAction()
{
        $filter_a = array('like'=>'a%');
        $filter_b = array('like'=>'b%');
}

এবং তারপরে আমার সমস্ত ফিল্টার ভেরিয়েবলের একটি অ্যারের বরাদ্দ করুন

public function testAction()
{
        $filter_a = array('like'=>'a%');
        $filter_b = array('like'=>'b%');
        echo(
        (string) 
        Mage::getModel('catalog/product')
        ->getCollection()
        ->addFieldToFilter('sku',array($filter_a,$filter_b))
        ->getSelect()
        );
}

সুস্পষ্ট হওয়ার স্বার্থে, ফিল্টার অ্যারেগুলির পূর্ব বর্ণিত অ্যারেটি এখানে।

array($filter_a,$filter_b)

এটি আমাদেরকে এমন একটি ক্লিউজ দেবে যা নীচের মত কিছু দেখাচ্ছে

WHERE (((e.sku like 'a%') or (e.sku like 'b%')))
  1. Varien_Data_Collection :: addFilter
 addFilter($field, $value, $type = 'and')

addFilter()কেবলমাত্র একটি একক ক্ষেত্রকে একটি একক মান এবং একটি ধরণের দ্বারা ফিল্টার করার অনুমতি দেয়। $typeযে কোনও হতে পারে:

  1. "এবং" (ডিফল্ট) - WHERE ধারাটিতে AND $ ক্ষেত্র = $ মান যুক্ত করে
  2. "বা" - WHERE ধারাটিতে "OR $ ক্ষেত্র = $ মান যুক্ত করে

আরও বিশদ দেখুন


1
এটি কিছুই ব্যাখ্যা করে না।
ফ্যাবিয়ান শেমংলার

এটি কোনও অর্থবোধ করে না। এটি এই পদ্ধতির পার্থক্য বর্ণনা করে না
লিন্ডার


2
আপনার আপডেট হওয়া উত্তরটি বেশিরভাগই অ্যালানস্টর্ম . com/મેজেন্টো_কলেকশন থেকে অনুলিপি করা হয় । কমপক্ষে আপনার উত্স উদ্ধৃত করুন!
ফ্যাবিয়ান শেমংলার
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.