cakephp pagination set condistion from array - cakephp

I am using a form with several check boxes i need to display only those data which is in check box category.
How to write conditions for that.
for($i=0;$i<count($this->request->data['filter']['delivering']);$i++)
{
$opt1=".'Gig.bangsalsodeliverings' => ".$this->request->data['filter']['delivering'][$i];
$opt2=$opt2.$opt1.',';
}
$options=array('conditions' => array($opt2));
$this->Paginator->settings = $options;
$agetGigsItem = $this->Paginator->paginate('Gig');
But getting error.
Thanks in advance

It seems you're using a string contatenation instead of array to build the conditions array.
Also it's not clear to me if the filter delivering is a set of strings or integers.
I guess you can try:
// Merge the filters into a csv string
$filters = array();
foreach($this->request->data['filter']['delivering'] as $v){
$filters[] = "'{$v}'";
}
$csv_filters = implode(",", $filters);
// Use the csv to make a IN condition
$this->Paginator->settings = array('conditions' => array(
"Gig.bangsasodeliverings IN ({$csv_filters})",
));
Please note that sql injection can be made here, so prepare your data before creating $csv_filters.

Related

Prestashop returns last value of imploded array from DB

I started fiddling with Prestashop 1.7 modules and I ran into this weird behavior.
I have this code to save values from form post to database (working ok)
protected function postProcess()
{
$form_values = $this->getConfigFormValues();
foreach (array_keys($form_values) as $key) {
Configuration::updateValue($key, Tools::getValue($key));
if($key == 'MSLT_MEGAMENU_CATEGORIES'){
$categories = implode(",",Tools::getValue($key));
Configuration::updateValue('MSLT_MEGAMENU_CATEGORIES', $categories);
}else{
$this->errors[]=$this->l('Please select categories to display');
}
}
}
And I use this code to fetch those values from database (works ok)
protected function getConfigFormValues()
{
$categories = explode(',',Configuration::get('MSLT_MEGAMENU_CATEGORIES', true));
return array(
'MSLT_MEGAMENU_LIVE_MODE' => Configuration::get('MSLT_MEGAMENU_LIVE_MODE', true),
'MSLT_MEGAMENU_CATEGORIES' => $categories,
'MSLT_MEGAMENU_ACCOUNT_EMAIL' => Configuration::get('MSLT_MEGAMENU_ACCOUNT_EMAIL', 'contact#prestashop.com'),
'MSLT_MEGAMENU_ACCOUNT_PASSWORD' => Configuration::get('MSLT_MEGAMENU_ACCOUNT_PASSWORD', null),
);
}
and helper to populate form with values
$helper->tpl_vars = array(
'fields_value' => $this->getConfigFormValues(), /* Add values for your inputs */
'languages' => $this->context->controller->getLanguages(),
'id_language' => $this->context->language->id,
);
return $helper->generateForm(array($this->getConfigForm()));
This is the var_dump() when trying to load values from database, for this case my DB value is (1,3,9)
array(1) { [0]=> string(1) "9" }
As you can see Configuration::get() only gets the last string value.
Interesting behavior is that when I update the data and stay in the same page, then everything is ok and data is fetched properly, but when I leave module configuration page and comeback, the issue happens. Maybe I am missing some little snippet of code? I am still a newbie. If needed I can provide more code.
I don't know what your specific goal is but in any case it is always convenient to use Prestashop's own functions.
To save and select the configuration variables
eg, save values in json format
Configuration::updateValue('MYVALUES', Tools::jsonEncode(Tools::getValue('MYVALUES')), true );
eg, get values
Tools::jsonDecode( Configuration::get( 'MYVALUES' );
Dirty workaround I found to get imploded values from DB correctly. Maybe someone will use it.
$sql = 'SELECT * FROM '._DB_PREFIX_.'configuration WHERE name = "MSLT_MEGAMENU_SELECTED_CAT"';
$value = Db::getInstance(_PS_USE_SQL_SLAVE_)->getRow($sql);
$selected = explode(',',$value['value']);

Cakephp 3 : How to get max amout row from a table

I have table call users , like
id name amount created
1 a 100 6-16-2016
2 b 200 5-16-2016
I need max amount full row, I have tried below code but getting syntax error.
$user = $this->Users->find('all',[
'fields' => array('MAX(Users.amount) AS amount'),
]);
simplest way
$user = $this->Users->find('all',[
'fields' => array('amount' => 'MAX(Users.id)'),
]);
using select instead of an options array
$user = $this->Users->find()
->select(['amount' => 'MAX(Users.id)']);
making use of cake SQL functions
$query = $this->Users->find();
$user = $query
->select(['amount' => $query->func()->max('Users.id')]);
the above three all give the same results
if you want to have a single record you have to call ->first() on the query object:
$user = $user->first();
$amount = $user->amount;
Simplest method using CakePHP 3:
$this->Model->find('all')->select('amount')->hydrate(false)->max('amount')
Will result in an array containing the maximum amount in that table column.
Is is better to disable hydration before getting the results, to get the results as an array, instead of entity. Below is a complete example of how to get the results in an array, with distinct steps:
//create query
$query = $this->Users->find('all',[
'fields' => array('amount' => 'MAX(Users.id)'),
]);
$query->enableHydration(false); // Results as arrays instead of entities
$results = $query->all(); // Get ResultSet that contains array data.
$maxAmount = $results->toList(); // Once we have a result set we can get all the rows

How to put where conditions with group by in cakephp find all query

I have created sql query which is working fine.
But i want to convert this sql query in cakephp format.
I try to convert this query in cakephp but
i am not understanding how to apply where conditions with group by clause.
And i only need to select this column u_data.lane_id AS LaneId, origin_city.pcode AS origin_pcode, dest_city.pcode AS dest_pcode....
not all columns from table.
plz help me to do this.
$options['conditions'] = array(
'CustomerRoute.portfolio_id' => '".$_SESSION["portfolioid"]."'
);
$content = $this->Customer->find('all', $options);
You simply need to define "group" and "fields" within $options-
Instead of $_SESSION, you should stick to the convention and use $this->Session->read instead.
//Eg: $_SESSION["portfolioid"] can be replaced with $this->Session->read("portfolioid")
$options['conditions'] = array(
"CustomerRoute.portfolio_id" => $this->Session->read("portfolioid"),
"u_data.supplier_id" => $this->Session->read("supplierid")
);
$options['fields'] = array(
"u_data.lane_id AS LaneId",
"origin_city.pcode AS origin_pcode",
"dest_city.pcode AS dest_pcode"
); // Add this
$options['group'] = array('CustomerRoute.id'); // Add this
$content = $this->Customer->find('all', $options);
This should give you what you're looking for.
Peace! xD

CakePhp foreach saving only last value in array

I have a problem, right now Im using this foreach loop on CakePhp on which I want to add all the values which are still not on the table for the respecting user. To give a little more context, the user has a menu. And the admin can select which one to add for the user to use. On the next code I receive a array with the menus which will be added as so:
//This is what comes on the ['UserMenuAccessibility'] array:
Array ( [menu_accessibility_id2] => 2 [menu_accessibility_id3] => 3 [menu_accessibility_id4] => 4 [menu_accessibility_id5] => 5 [menu_accessibility_id8] => 8 )
I get the ids of the menus which want to be added to the table for the user to use. And I use the next code to add the menus to the table if they are not there still:
//I check if the array has something cause it can come with no ids.
if (!(isset($this->request->data['UserMenuAccessibility']))) {
$this->request->data['UserMenuAccessibility'] = array();
}
$UserMenuAccessibility = $this->request->data['UserMenuAccessibility'];
foreach ($UserMenuAccessibility as $key => $value) {
$conditions = array(
'UserMenuAccessibility.menu_accessibility_id' => $value,
'UserMenuAccessibility.users_id' => $id
);
if ($this->User->UserMenuAccessibility->hasAny($conditions)) {
} else {
$valuemenu['UserMenuAccessibility']['users_id'] = $id;
$valuemenu['UserMenuAccessibility']['menu_accessibility_id'] = $value;
if ($this->User->UserMenuAccessibility->save($valuemenu)) {
} else {
$this->Session->setFlash(__('The user could not be saved. Please, try again.'));
}
}
}
For some reason the array is only saving the last new id which is not on the table and not the rest. For example if I have menu 1 and 2 and add 3 and 4 only 4 gets added to the table. For some reason I cant add all the missing menu ids to the table. Any ideas why this is happening?
Thanks for the help on advance.
It looks like your code will save each item, but each call to save() is overwriting the last entry added as $this->User->UserMenuAccessibility->id is set after the first save and will be used for subsequent saves. Try calling $this->User->UserMenuAccessibility->create() before each save to ensure that the model data is reset and ready to accept new data:-
$valuemenu['UserMenuAccessibility']['users_id'] = $id;
$valuemenu['UserMenuAccessibility']['menu_accessibility_id'] = $value;
$this->User->UserMenuAccessibility->create();
if ($this->User->UserMenuAccessibility->save($valuemenu)) {
}
In cakephp 2.0 $this->Model->create() create work fine. But if you are using cakephp version 3 or greater then 3. Then follow the below code
$saveData['itemId'] = 1;
$saveData['qty'] = 2;
$saveData['type'] = '0';
$saveData['status'] = 'active';
$saveData = $this->Model->newEntity($saveData);
$this->Model->save($materialmismatch);
In normal case we use patchEntity
$this->Model->patchEntity($saveData, $this->request->data);
It will only save last values of array so you have to use newEntity() with data
In cakephp3, patchEntity() is normally used. However, when using it for inserting-new/updating entries in a foreach loop, I too saw that it only saves the last element of the array.
What worked for me was using patchEntities(), which as explained in the patchEntity() doc, is used for patching multiple entities at once.
So simplifying and going by the original code sample to handle multiple entities, it could be:
$userMenuAccessibilityObject = TableRegistry::get('UserMenuAccessibility');
foreach ($UserMenuAccessibility as $key => $value) {
$userMenuAccessibility = $userMenuAccessibilityObject->get($value);//get original individual entity if exists
$userMenuAccessibilities[] = $userMenuAccessibility;
$dataToPatch = [
'menu_accessibility_id' => $value,
'users_id' => $id
]//store corresponding entity data in array for patching after foreach
$userMenuAccessibilitiesData[] = $dataToPatch;
}
$userMenuAccessibilities = $userMenuAccessibilityObject->patchEntities($userMenuAccessibilities, $userMenuAccessibilities);
if ($userMenuAccessibilityObject->saveMany($requisitions)) {
} else {
$this->Session->setFlash(__('The users could not be saved. Please, try again.'));
}
Note: I haven't made it handle if entity doesn't exist, create a new one and resume. That can be done with a simple if condition.

Find CakePHP - different query criteria

I have a simple search form with 3 data and now not all data needs to be filled, some may stay empty ...
as they filled :
$this->Praca->find('all',array(
'conditions'=>array(
'kategoria'=>$wyniki['kategoria'][0],
'wojewodztwo'=>$wyniki['wojewodztwo'],
'poziom'=>$wyniki['poziom']
)));
Now, fe. when $wyniki['kategoria'] is empty I must :
$this->Praca->find('all',array(
'conditions'=>array(
'wojewodztwo'=>$wyniki['wojewodztwo'],
'poziom'=>$wyniki['poziom']
)));
To many possibilities, I need to find a SMART way, any idea? :)
try this
$conditions = array();
if(!empty($wyniki['kategoria'][0])){
$conditions = array('kategoria'=>$wyniki['kategoria'][0]);
}
and so on...
........
$this->Praca->find('all', compact('conditions'));
In Fazel way you need to add conditions per each node. But case below you can add conditions as many as you want
$conditions = array();
$i=1;
foreach ($wyniki as $key=>$wyn){
if(!empty($wyniki[$key])){
$conditions[$i++] = array($key=>$wyn); //or array($key=>end($wyn))
}
}
$this->Praca->find('all',array('conditions'=>$conditions));

Resources