$this->Model->save() : what's is wrong with this code? - php

I am a beginner in cakePHP , i want to save some data into my database , but i always get : the Message : Sorry, Error while saving data.
Here is my code : ( Controller : UsersController.php : ( and i have added the Model 'UserState to the array $uses )
if($onbreak == 'true'){
$userStatus = 1;
//$response['userStatus'] = 1;
} else {
$userStatus = 0;
//$response['userStatus'] = 0;
}
//add the new user_status to the $newUserState
$newUserState['UserState']['user_id'] = $userID;// $userID = 1
$newUserState['UserState']['user_status'] = $userStatus;
//adding values for fields which should not be NULL
$newUserState['UserState']['user_phone_nb'] = '4343';
//
saving data
if($this->UserState->save($newUserState)){
$response['success'] = 'true';
$response['message'] = '';
}else{
$response['success'] = 'false';
$response['message'] = 'Sorry, Error while saving data.';
}
Thanks in advance
EDIT :
Structure of the table userstates :
id : BIGINT primary key AUTO INCREMENT,
user_id : INT NOT NULL,
user_status : SMALLINT NOT NULL,
user_phone_nb = VARCHAR(15) NULL
the Model Userstate :
class Userstate extends AppModel {
var $useTable = 'userstates';
public $name = 'UserState';
}
EDIT 2 :
when i debugg the variable $newUserState i got this ( which seems that is OK ) :
Array
(
[UserState] => Array
(
[user_id] => 18
[user_status] => 0
[user_phone_nb] => 4343
)
)

I'm not sure what you are doing here,
could you post your table structure and the insert-query cake is generating? You find that on the bottom if you use the standard cake-layout and have debugging mode on.
I suspect (but am not sure without further data) that there is another field in the table wich needs a value (cannot be null).

I am assuming the field in the DB is 'userStatus' and there is only one value to save. But this should work and you should be able to expand on it to save other values.
Hope this helps.
Saving a new Record
if($onbreak == 'true'){
$userStatus = 1;
} else {
$userStatus = 0;
}
//add the new user_status to the $newUserState
$newUserState['UserState']['user_id'] = $userID;// $userID = 1
$newUserState['UserState']['user_status'] = $userStatus;
//adding values for fields which should not be NULL
$newUserState['UserState']['user_phone_nb'] = ' ';
// Must include id as it is a primary Key and thus required for saving.
$newUserState['UserState']['id'] = $userstate_id;
//saving data
if($this->UserState->save($newUserState)){
$response['success'] = 'true';
$response['message'] = '';
}else{
$response['success'] = 'false';
$response['message'] = 'Sorry, Error while saving data.';
}
Ok try this.
Rename your Model to user_state.php
Then add the following to it, based on Cake 1.2 cookbook
http://book.cakephp.org/view/436/useTable
<?php
class Userstate extends AppModel {
var $useTable = 'userstates';
public $name = 'UserState';
}
Also in the config/core.php make sure the line with debug reads as follows.
Configure::write('debug', 2);
Try this and let me know your results.

Does this work for you:
$this->UserState->set('UserStatus', 'New title for the article');
$this->UserState->save();
I hope it helps

i found the solution,
in my Model , i have the variable $validate with some parameters which have the required variable setted to true. so i've three Solutions :
First :
just commenting the variable and dont use it ^^
Second:
just initialize the required variables with a default value.
Third :
i found that in the doc , we can tell cakePHP to save our data without perform validation :
save(array
$donnees = null, boolean $valider = true, array $listeDesChamps = array())
so all what i did is saving data and passing the second parameter with a false value like this : $this->UserState->save($newUserState, false); , ( personally i've used this Third Solution ^^ )
Thanks you all for your help :)
Regards,

Some tips at the end:
For cases like these it's nice to have multiple validation sets made possbile by this: http://bakery.cakephp.org/articles/dardosordi/2008/07/29/multivalidatablebehavior-using-many-validation-rulesets-per-model
Next time post complete code. The validation thing would be first guessed if you hadn't post just a 4 line represenation of your model which everyone thought was final.
You should reinclude the sql dump in your layout. It will not show up in live mode due of DEBUG => 0 and will help you enormous in situation like these.
I think the class name of the UserState model should be "UserState" and like already mentioned the file name "user_state.php". That would save a line of code :P
Greetings
func0der

Related

Incorrect integer value: '{"id":1,"name":"Main Lab}' for column 'lab_id' at row 1

I get this error Incorrect integer value for column 'lab_id' at row 1
with dd($lab)
it returns 1
but if I fill the form and click submet it returns the error
it should be gettin from mount function?
how can I fix that?
can any one help?
public function submit()
{
$this->validate();
$this->sample->received_at = now();
$this->sample->lab_id = $this->lab;
$this->sample->save();
$this->message = "Sample {$this->samples->sample_id} Registered Successfully";
}
Shouldn't it be $this->lab->id :
$this->sample->lab_id = $this->lab;
When you set $this->lab = Lab::find($lab);, then $this->lab is an Eloquent model, not just a single id. You need to assign just the id from that model to the sample that you're creating.
$this->sample->lab_id = $this->lab->id;

Database data field check before Data insertion

I have a data coming from the HTML Page. And i want to check whether the date and the place values already exists. If they exists, it should throw an error saying Data is already present, if those date and place data is not there it should allow the user to save it.
Here is the code which i have written to save it,
public function StoreSampling(Request $request)
{
$date = Carbon::createFromFormat('d-m-Y', $request->input('date'))->format('Y-m-d');
$doctorname = Input::get('doctorselected');
$product = Input::get('product');
$product= implode(',', $product);
$quantity = Input::get('qty');
$quantity =implode(',',$quantity);
$representativeid = Input::get('representativeid');
//Store all the parameters.
$samplingOrder = new SamplingOrder();
$samplingOrder->date = $date;
$samplingOrder->doctorselected = $doctorname;
$samplingOrder->products = $product;
$samplingOrder->quantity = $quantity;
$samplingOrder->representativeid = $representativeid;
$samplingOrder->save();
return redirect()->back()->with('success',true);
}
I searched some of the Stack over flow pages. And came across finding the existence through the ID And here is the sample,
$count = DB::table('teammembersall')
->where('TeamId', $teamNameSelectBoxInTeamMembers)
->where('UserId', $userNameSelectBoxInTeamMembers)
->count();
if ($count > 0){
// This user already in a team
//send error message
} else {
DB::table('teammembersall')->insert($data);
}
But i want to compare the date and the place. And if they are not present, i want to let the user to save it. Basically trying to stop the duplicate entries.
Please help me with this.
There are very good helper functions for this called firstOrNew and firstOrCreate, the latter will directly create it, while the first one you will need to explicitly call save. So I would go with the following:
$order = SamplingOrder::firstOrNew([
'date' => $date,
'place' => $place
], [
'doctorname' => Input::get('doctorselected'),
'product' => implode(',', Input::get('product')),
'quantity' => implode(',',Input::get('qty')),
'representativeid' => Input::get('representativeid')
]);
if($order->exists()) {
// throw error
return;
}
$order->save();
// success
You need to modify your query to something like this:
$userAlreadyInTeam = SamplingOrder::where('date', $date)
->where('place', $place) // I'm not sure what the attribute name is for this as not mentioned in question
// any other conditions
->exists();
if (userAlreadyInTeam) {
// Handle error
} else {
// Create
}
You do not need to use count() as your only trying to determine existence.
Also consider adding a multi column unique attribute to your database, to guarantee that you don't have a member with the same data and place.
The best way is to use the laravel unique validation on multiple columns. Take a look at this.
I'm presuming that id is your primary key and in the sampling_orders table. The validation rule looks like this:
'date' => ['unique:sampling_orders,date,'.$date.',NULL,id,place,'.$place]
p.s: I do not see any place input in your StoreSampling()

Laravel - can't find() attached object in many-to-many relationship

in my POST form users are able to add other users to a room.
I put a unique constraint on the link (no duplicate entry in the link between users and rooms).
However when I refresh my page (f5) after submitting the form, Laravel complains about duplicate entries, although I do check if the objects are attached before.
Here's the code:
$roomUsers = Room::find($request->room_id)->users();
if ($request->add != null) {
foreach ($request->add as $uId)
// if null, user hasnt been attach yet
if (!$roomUsers->find($uId)) {
Log::debug($roomUsers->find($uId) == null ? 'null' : 'not null');
// then we can attach him
$roomUsers->attach($uId);
}
}
The line !$roomUsers->find($uId) returns true yet the object has been attached in the previous iteration. How is that possible ? Thanks
The reason you're above code isn't working is because you're not creating a new instance of BelongsToMany for each check. This means that every time you call find you're not actually creating a new query you're just adding to the existing one e.g.
say you the ids to add are [1, 2, 3] by the last check your query would effectively be:
SELECT * FROM users WHERE id = 1 AND id = 2 AND id = 3
To keep with the above logic you could do:
$room = Room::find($request->room_id);
if ($request->add != null) {
foreach ($request->add as $uId)
// if null, user hasnt been attach yet
if (!$room->users()->find($uId)) {
// then we can attach him
$room->users()->attach($uId);
}
}
Or a much simpler way to go about this would be to syncWithoutDetaching.
Your code could then look something like:
$roomUsers = Room::find($request->room_id);
if ($request->has('add')) {
$roomUsers->users()->syncWithoutDetaching($request->add);
}
Hope this helps!

I am trying to update but it is adding a new row

this is my code for updating:
PS: empid is a foreign key but i think that shouldnt be the reason and the code is in CakePHP
if($this->request->is('post'))
{
$this->request->data["Leave"]["empid"] = $this->request->data["id"];
$this->Leave->empid = $this->request->data["Leave"]["empid"];
$this->request->data["Leave"]["leave_start"] = $this->request->data["start_date"];
$this->request->data["Leave"]["leave_end"] = $this->request->data["end_date"];
$this->request->data["Leave"]["leave_taken"] = $this->request->data["leave_taken"];
if($this->Leave->save($this->request->data['Leave']))
{
return $this->redirect(array('action' => 'manage_leave'));
}
}
// This code is inserting a new row instead of updating and also not adding any value in the new row
May be your trying to update the foreign table data using simple save.
Update multiple records for foreign key
Model::updateAll(array $fields, mixed $conditions)
Example
$this->Ticket->updateAll(
array('Ticket.status' => "'closed'"),
array('Ticket.customer_id' => 453)
);
Simple save for the primary key
Make sure that your HTML has empid
echo $this->Form->input('Leave.empid', array('type' => 'hidden'));
Save Model
$this->Leave->empid = $this->request->data["Leave"]["empid"]; //2
$this->Leave->save($this->request->data);
In between, you can also try to set the model data and check the $this->Leave->validates() and $this->Leave->validationError if they are giving any validation errors.
// Create: id isn't set or is null
$this->Recipe->create();
$this->Recipe->save($this->request->data);
// Update: id is set to a numerical value
$this->Recipe->id = 2;
$this->Recipe->save($this->request->data);
You can find more information about all Saving your data
Hope this helps you :)
And in case if $empid is primary key of corresponding table of Leave model (e.g leaves), Just replace:
$this->Leave->empid = $this->request->data["Leave"]["empid"];
By
$this->Leave->id = $this->request->data["Leave"]["empid"];

CakePHP: Why am I unable to update record with set() or save()?

I've been trying all night to update a record like this:
$r = $this->Question->read(NULL, $question['Question']['id']);
debug($r);// This is a complete Question array
$this->Question->set('status', 'version');
$s = $this->Question->save();
//$s = $this->Question->save($r['Question']);//this also doesn't work
debug($s); // = False every time!! Why??
exit;
The two comments show variations I've tried but didn't work either.
#Dipesh:
$this->data = $this->Question->read(NULL, $question['Question']['id']);
$this->Question->status = 'version';
$s = $this->Question->save($this->data);
debug($s);
exit;
#Dipesh II:
$this->request->data = $this->Question->read(NULL, $question['Question']['id']);
debug($this->data);
//$this->Question->status = 'version';
$this->request->data['Question']['status'] = 'version';
$s = $this->Question->save($this->request->data);
//$s = $this->Question->save($r['Question']);
debug($s);
exit;
#Dipesh III:
(removed)
cakePHP provide a method called set() in both Models::set() as well as in Controller::set();
About Controller::set()
This method is used to set variables for view level from any of the controller method. For example fetching records and from models and setting them for views to display it to clients, like this
$data = $this->{ModelName}->find('first');
$this->set('dataForView',$data) // now you can access $data in your view as $dataForView
About Model::set()
This method is used to set data upon a model, the format of the array that will be passed must be same as that used in Model::save() method i.e. like this
$dataFormModel = array('ModelName'=>array('col_name'=>$colValue));
$this->{ModelName}->set($dataForModel);
Model::set() will accept its parameter only in this format, once successfully set you can do following
validate this data against the validation rules specified in model directly like this
$isValid = $this->ModelName->validate();
save/update data by calling Model::save()
Use $this->data instead of $r
Example
$this->data = $this->Question->read(NULL, $question['Question']['id']);
$this->set is used to set variable value and pass it to view so view can access it where as $this->data represent the data to be stored in database.
If You're using Cake 2.0 then replace $this->data which is read only in Cake 2.0 to $this->request->data.
It's not very "automagical" but I was able to get this working like this:
$set_perm_id = 42;//who cares
$data = array(
'Question'=> array(
'id'=> $question['Question']['id'],
'perm_id'=> $set_perm_id,
'status'=>'version'
)
);
$s=$this->Question->save($data);
Basically I'm just building the data array manually. If anyone knows why this works instead of what I was doing before, I'd love to hear it.
Just try these lines..
$this->Question->id = $question['Question']['id'];
$this->Question->set('status','version');
$this->Question->save();
OR
$aUpdate["id"] = $question['Question']['id'];
$aUpdate["status"] = "version";
$this->Question->save($aUpdate);

Categories