5

I have a huge catalog and I've enabled "Display out of stock products" to show the out of stock products too in the listing page. Since my catalog is huge and 80% of the products are out of stock, I would like to show only the out of stock products which were created in the last 6 months.

In the listing page I was able to do this by checking the product stock status and product created date. But the problem with this is that the products which do not meet the conditions of the filter are still counted in the product collection but are displayed as a blank space. For eg: if the default number of product displayed in the listing page is set to 12 and if only 10 products meet the above conditions, there are two blank spaces at the end for the left out products. Is there a way to avoid these blank spaces?

EDIT: code used in list.phtml

$_productCollection=$this->getLoadedProductCollection();
$currentDate = date("Y-m-d");
$check_date = new DateTime($currentDate);
$check_date->modify("-180 day"); // 6 months
$check_date = $check_date->format("Y-m-d");
foreach ($_productCollection as $_product):
    $pdt_date = substr($_product->getData('created_at'),0,10);
    if(!$_product->isSaleable() && ($pdt_date < $check_date)):
        //don't show the product
    else:
        //display product
    endif;
endforeach;
2

So lets start with the obvious issue you have: The blank spaces. The issue, as you already know, is that your collection contains the count of products that are not to be displayed (as per your code conditional filtering) Hence the toolbar object contains the wrong count now, as per your actual product display.

That is just but one issue that would arise. Another is that your page count will be wrong. I am sure there will be other discrepancies.

Additionally yoru 'filtering by code' in the .phtml will create an unwanted overhead. Small, but on a busy site, compounding. With Magento is what it is, every bit (pun intended) of lost resources, is a problem.

Your wanted solution, to adjust the collection, and filter them out 'at the source' is the right move.

However:

As noted by @AmitBera, placing your code inside the .phtml is the wrong move. You are setting your self up for later fail - especially with upgradability of your site. You will have to spend time re-integrating your solution to new magento version .phtml files. Not such a big deal with M1 these days, as there is not going to be many (if at all any further) upgrades going forward. M2 is the path now.

However, It is still best to move your code to the observer method as described. The same problem will exists if you opt for a new theme, and keep on M1 for a while longer.

Secondly, your want to filter by date ranges would most likely require you to continuously adjust the code going forward. By your own statement, you have a lot of products. If you filter the collection today, using a start date, going 6 months back, you will obviously be at 7 months back in 1 month, 8 months in 2 months time time, etc etc. You will eventually reach the same problem

This will require continuous adjustment, which is not ideal at all.

An alternative approach is to filter by X days back, from the day the list is viewed. For your 6 months period, you can make that 182.5 days, thus keeping your display rock solid on a 6 month display period, calculated from the current date. No continuous updates required.

Filtering going X days back is really easy. :)

This is an extract from my Dynamic Category Products Extension, (yes blatant punt, cannot help myself!) which allows you to set rules on categories, and populate products to the category that validates to the given rule(s)

In this code the following variables would have existed prior to the code shown.

  • $collection is a product collection, derived from the current active category. This is gotten by calling : Mage::getModel('catalog/category')->load($category_id)->getProductCollection(); It is still a product collection, just derived from a different source object. Will be compatible with your product collection.
  • $value is the days to go back. in your case : 182.5 days
  • $attrCode is whatever attribute code you want to filter on. Be it created_at, updated_at etc

The code is very straight forward. Please ask if you need any clarification.

$days = ($value == 1)
                    ? 'day'
                    : 'days';
$todayDate = Mage::app()->getLocale()->date()->toString(
                Varien_Date::DATE_INTERNAL_FORMAT
            );
    $startDate = date('Y-m-d',
                        strtotime(
                            '-' . $value . ' ' . $days,
                            strtotime($todayDate)
                        )
                    );
   $collection->addAttributeToFilter(
                 array(
                    array(
                          'attribute' => $attrCode,
                          'gteq' => $startDate,
                          'date' => true
                         )
                    )
                 );
   $collection->addAttributeToFilter(
                array(
                   array(
                         'attribute' => $attrCode,
                         'notnull' => true
                        ),
                   )
               );

I hope that helps.

PS: Do consider my extension, it will save you heaps of time, especially managing a large catalog. It does not cost much.

0

It possible, but

Enable out of stock product from admin:


you need to enable setting for show out of stock product by default.

Enable out of stock product

then using Magento event/observer,We can filter collection by in stock.

Event: catalog_product_collection_load_after.Perform this event only for frontend by add code inside frontend tab

<frontend>
<events>
    <catalog_product_collection_load_after>
    <observers>
        <countryfilter>
        <class>mymoduleMOdelprefix/observer</class>
        <method>filterBYCountry</method>
        </countryfilter>
    </observers>
    </catalog_product_collection_load_after>
</frontend>

According to magento system,a product collection filter by in stock by using below code:

Mage::getSingleton('cataloginventory/stock')->addInStockFilterToCollection($_productCollection);

Now if we add below code at observer and enable disable product collection by period

Observer code where collection is filtered :

<?php class MyNamespacr_Mymodule_Model_Observer
    public function filterBYCountry($observer)
    {
        $collection = $observer->getEvent()->getCollection();
        /* @var $collection Mage_Catalog_Model_Resource_Eav_Mysql4_Product_Collection */
        /* d here join with your atble
    if($TimePeriod is match):
    else:
    /*  not  show only in stock product */
    Mage::getSingleton('cataloginventory/stock')->addInStockFilterToCollection($collection);
    endif;
        return $this; } }
  • Hi Amith, I am actually not filtering the collection with my conditions, i am just checking it in the list.phtml. I have edited my question with the code i am using in list.phtml. How do I apply the 6 months time filter to the collection in your observer? – James Feb 27 '15 at 7:17
  • james it not good idea to filter at list phtml – Amit Bera Feb 27 '15 at 7:21
  • Hi, i suggesting to you,instead of do this code at list.html.Why you do use cron. Create php shell and on script you will etc all out of stock product with more 180 days over then disable the product.If do apply the 6 months time filter to the collection in my observer then it should create issue on your site performance. – Amit Bera Feb 27 '15 at 7:34
  • Amith I don't want to disable the products. Is there some other way to filter the loadedProductCollection to include the out of stock products which were created in the last 6 months? Also how do I check the date of creation of each product in the collection? – James Feb 27 '15 at 9:53
  • 1
    let me check............. – Amit Bera Feb 27 '15 at 9:54

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.