Apply filter on collection Object - magento

I am getting this object on list page
$_productCollection=$this->getLoadedProductCollection();
//return 3 records
now I applied filter as
$_productCollection=$_productCollection->addFieldToFilter('genre', array('finset' => '126'));
//now it should return 1 record
but it gives me a count of 3. Now, if I run the query in database by getting the query using echo $_productCollection->getSelect(); it returns 1 record.
Can anybody help me to resolve this?

Most likely this doesn't work because $this->getLoadedProductCollection() returns a collection which already has been loaded by the catalog/layer singleton.
But you could override Mage_Catalog_Model_Layer::prepareProductCollection() to get in control and add the custom filters you want.

Related

$operations = Operation::findOrFail(2)->get(); return 6 results

I'm trying to get the operation that as PK id = 2
$operations = Operation::findOrFail(2)->get();
This line should do the trick, but I get all my 6 operations as result...
Off course, my other 5 has ID value from 1 to 6, they doesn't match.
I checked Operation is a model with no custom config, and Operation table has been created by migration and has ID as PK...
Off course, I could change it with another eloquent query, but this should work and I would love to know why it is failing.
What am I missing ?
remove ->get() it will should be
$operations = Operation::with('meters')->findOrFail(2);
get() gives you a collection which is all data of Operation to get single instace you should remove get()

How to exclude product(s) from search result programatically in Magento

I'm trying to exclude products from populating the search result.
It seems to be working fine on my localhost but not on clients dev server.
I'm observing the event
catalog_block_product_list_collection
and in observer method, in the end is this code:
$observer->getCollection()
->addFieldToFilter('entity_id', array('nin' => array_keys($_excludeProducts)))
->clear()
->load();
which works for catalog as well and search result list but for the moment not on search result list on clients dev server.
Any guidance/help is greatly appreciated.
Edit: Debugging this method gives me an empty collection but still the data is populating from somewhere.
I've changed the approach and used another event: catalog_product_collection_load_before
found better method to implement the approach with less code. #optimization
$excludeIds = array(2,3,4); //$excludeIds mixed
$observer->getCollection()
->addIdFilter($excludeIds, true); //exclude = true
The event also helps in keeping the correct items count on toolbar as it is dispatched before collection load.
I ran into a similar issue when trying to filter this collection using this event.
Do you have flat categories and flat products set the same in both environments? In my case, my code would only work with flat tables OFF, since I was using joining other EAV attributes.
In your case, if you are using flat, I think you just need to do addAttributeToFilter() instead.
In my case, here is what my observer looks like:
function onCategoryCollectionLoad($observer) {
$collection = $observer->getEvent()->getCategoryCollection();
$customerGroupId = (int) Mage::getSingleton('customer/session')->getCustomerGroupId();
// hidden_from_groups is an EAV attribute; I couldn't figure out how to make it work with flat because it has a backend_model
$collection->addAttributeToSelect('hidden_from_groups');
$collection->addExpressionAttributeToSelect('should_be_hidden', "COALESCE(FIND_IN_SET($customerGroupId, {{attribute}}), 0)", 'hidden_from_groups');
// should_be_hidden is not a real db field (nor EAV attribute); it only exists because of the addExpressionAttributeToSelect() above.
$collection->addFieldToFilter('should_be_hidden', array('lt' => 1));
// I don't call $collection->load(); that will get called further down the line.
}

Laravel Paginator getTotal returns null - Need total record count for all pages

I have implemented simple pagination using laravel. It works fine. However, I want to add total number of records and trying to use the method getTotal() but it returns null value.
$records = DB::table('tablename')
->where(condition)
....
....
->simplePaginate(10);
In the view, adding links works fine.
{{$records->links();}}
When I use,
{{$records->getTotal();}}
it returns null.
If I use,
{{$records->count();}}
it returns the count of records for a given page.
Any insights please?
That's how simplePaginate works. From the docs:
If you are only showing "Next" and "Previous" links in your pagination view, you have the option of using the simplePaginate method to perform a more efficient query. This is useful for larger datasets when you do not require the display of exact page numbers on your view.
The simple method is simple because it doesn't need to do the extra, inefficient-on-large-tables count query to obtain the total.
There is method total() in that pagination object. Just call that object. You will get total count.
ex: $records->total();
I had the same problem, what I did was
$records = DB::table('tablename')
->where(condition)
....
....
->paginate(1); //set as 1
$total = $records->getTotal(); //get total
Then returning it like this(I am using ajax that is why I return it as array):
return Response::JSON(array(
'pagination' => (string) $records->links('pagination::simple'),
'total_records' => $total
));

How to check values before update in Eloquent?

When using updating via Eloquent it returns affected rows as a result. Is it possible somehow to get status of update? For example if I passing some bad id in WHERE it still return 0 affected rows, though here I need to know that this id does not exist. Basically when the user clicks a save button, but nothing edit - I get 0 affected rows from Eloquent and also when bad id is entered. I need to somehow separate this things.
You could check first if the WHERE returns anything:
if(Model::where($where)->count() > 0){
// row(s) found > do update
}
else {
// where doesn't match any rows
}

CakePHP Pagination sort() on Related Models

I have two models: Plans and PlanDetails.
Relationship is: PlanDetails hasMany Plans. Plans belongTo PlanDetails.
In the PlanDetails view.ctp, I am pulling in related Plans.
I am trying to sort the Plans by ANY field (I've tried them all), and I cannot get it working. I assume I am overlooking something very simple.
Here is my base code:
PlanDetail >> view.ctp:
...foreach ($planDetail['Plan'] as $plan_edit) :
$class = null;
if ($i++ % 2 == 0) {
$class = ' class="altrow"';
}...
<?php echo $this->Paginator->sort('Plan ID', 'Plan.id'); ?>...
...<?php echo $plan_edit['id']; ?>
plan_details_controller.php:
...function view($id = null) {
if (!$id) {
$this->Session->setFlash(__('Invalid plan detail', true));
$this->redirect(array('action' => 'index'));
}
$this->PlanDetail->recursive = 2; // To run the editable form deeper.
$this->set('planDetail', $this->PlanDetail->read(null, $id));
$this->set('plan', $this->paginate('Plan'));
}...
I should add, no errors are being thrown and the sort() arrows on the ID field are showing as expected, but the sort order DOES not change when clicked either way.
Sorry, I'm not able to comment on the question itself, but I've noticed that in your action, you set planDetail to be the PlanDetail record you read (with recursive set to 2), and then you set plan to be the result of the paginate call.
Then, in your view template, you're iterating over $planDetail's contained Plan association, like this:
foreach ($planDetail['Plan'] as $plan_edit):
But in order to get the sorting and pagination done, you need to be displaying the results of the paginate call i.e. iterate over the records contained in $plan.
Do a debug($plan) in your view template to see what results you get there and to see if the records' ordering changes when you sort by different fields.
Also, perhaps you're using syntax I'm not aware of, but if you simply call $this->paginate('Plan') in your controller, I don't know that you're going to get only the related Plan records for your particular PlanDetail record. (There's nothing tying the $id passed into your view action with the Plan records.) You might need to add some conditions to the paginate call, like so:
$this->paginate['Plan'] = array('conditions' => array('Plan.plan_detail_id' => $id));
$this->set('plans', $this->paginate('Plan'));
Here is what I did to solve this. Based on some helpful direction from johnp & tokes.
plan_details/view.ctp:
...$i = 0;
foreach ($plan as $plan_edit) : // note $plan here.
}...
In my plan_details_controller.php view action:
$conditions = array("Plan.plan_detail_id" => "$id");
$this->set('plan', $this->paginate('Plan', $conditions)); // note "plan" in the first argument of set (this is required to pass the results back to the view). Also. The $condition is set to return ONLY plans that match the plan_detail_id of id (on the plan_details table).
And in my view, in order to get my results (because I changed the array name), I had to change the way I was getting the values to:
$plan_edit['Plan']['modified'] // note I placed ['Plan'] in front of these calls as the array called for this to get the data...
Well until the next problem! SOLVED.

Resources