This question already has answers here:
Why does this PDO statement silently fail?
(2 answers)
Closed 18 days ago.
I'm using the following php pdo code to insert data into mysql database, the insertion succeeded, however, the updated database is showing the string literals ':a', ':b' as values in respectively field. what's wrong?
$data = array(
array('a' => 'John', 'b' => 'OK'),
);
$st=$dbh->prepare("insert into mytable (a, b) values(':a', ':b')");
$st->execute($data) or print_r($st->errorInfo());
Remove the quotes from your placeholders. Otherwise, they are treated as string literals and directly inserted.
$st=$dbh->prepare("insert into mytable (a, b) values(:a, :b)");
And remove the nesting on your array:
// $data is an associative array, it should not contain another array!
$data = array('a' => 'John', 'b' => 'OK');
To be consistent, I prefer to use the : on the placeholder array keys:
$data = array(':a' => 'John', ':b' => 'OK');
You need to define your array the same in the sql and the parameters, you're missing the ":". You also don't need two arrays, only one.
$data = array(':a' => 'John', ':b' => 'OK');
The query also does not need quotes, since PDO already knows it's a parameter
$st=$dbh->prepare("insert into mytable (a, b) values(:a, :b)");
$st->execute($data) or print_r($st->errorInfo());
You are executing a prepared statement with named placeholders. So, you need to remove quotes from your placeholders, otherwise they are treated as a values for respective columns and directly updated.
To be consistent, I prefer to use the : on the placeholder array keys:
$data = array(':a' => 'John', ':b' => 'OK');
$st=$dbh->prepare("insert into mytable (a, b) values(:a, :b)");
You can also execute a prepared statement with question mark placeholders:
$data = array(
array('John','OK'),
);
$st=$dbh->prepare("insert into mytable (a, b) values(?, ?)");
$st->execute($data) or print_r($st->errorInfo());
Related
I want to insert or update rows into my models table. But can't figure out the query.
SmStudentAttendance This is my model.
$students is my collection.
I have put the collection fields in arrays.
foreach ($students as $student) {
array_push($temp_id, $student->id);
array_push($temp_lastname, $student->last_name);
array_push($temp_academic_id, $student->academic_id);
array_push($temp_attendance, 'P');
array_push($temp_attendancedate, $date);
array_push($temp_schoolid, '1');
array_push($temp_updatedby, '1');
array_push($temp_createdby, '1');
}
Now I want to insert them if a row for the student_id and attendance_date is not present in the table else update if it already exists.
This is the query:
SmStudentAttendance::upsert('attendance_type', $temp_attendance, 'attendance_date', $temp_attendancedate, 'student_id', $temp_id, 'created_by', $temp_createdby, 'updated_by', $temp_updatedby, 'school_id', $temp_schoolid, 'academic_id', $temp_academic_id);
Error I am geting:
Argument 1 passed to Illuminate\Database\Eloquent\Builder::upsert() must be of the type array, string given, called in D:\xampp\htdocs\sms\vendor\laravel\framework\src\Illuminate\Support\Traits\ForwardsCalls.php on line 23
You're creating your arrays for columns rather than rows, this will cause problems, consider this code instead:
$studentRows = [];
foreach ($students as $student) {
$studentRows[] = [
'id' => $student->id,
'last_name' => $student->last_name,
'academic_id' => $student->academic_id,
'attendance_type' => 'P',
'attendance_date' => $date,
// .... rest of the fields
]
}
SmStudentAttendance::upsert($studentRows, [ 'id', 'last_name', 'academic_id' ], [ 'attendance_type', 'attendance_date' ]);
In general the idea is you pass it an array of rows you want to upsert, then an array of fields to match and an array of fields to update. Then Laravel will make queries find all rows that match the fields specified and update those and then insert the rows that did not match the given fields.
The error message, "Argument 1 passed to Illuminate\Database\Eloquent\Builder::upsert() must be of the type array, string given", suggests that the first parameter needs to be an array rather than the string you are setting.
Take a look at the documentation for this at https://laravel.com/docs/8.x/eloquent#upserts for an example. The method accepts two arrays. The first contains all of the data to be updated, the second the fields which uniquely identify the record. You will need to update your method call to match this syntax.
I'm updating a record in this way:
Yii::$app->db->createCommand()->update('table', ['config' => json_encode($array)],
'field1 = :field1', [':field1' => $field1]
)->execute();
My aim is to add an extra condition with the AND operator but I don't know how to do it.
I've followed this example: LINK
// UPDATE (table name, column values, condition)
Yii::$app->db->createCommand()->update('user', ['status' => 1], 'age > 30')->execute();
But it doesn't show a lot of possibilities.
try this way
Yii::$app->db->createCommand()
->update('table', ['config' => json_encode($array)],
'field1 = :field1 AND field2 = :field2',[':field1' => $field1,':field2' => $field2])
->execute();
Just like an array, with each condition separated by a ,.
In your case:
Yii::$app->db->createCommand()->update(
'table',
['config' => json_encode($array)],
['field1' => $field1, 'field2' => $field2]
)->execute();
Note that with this syntax you don't need to bind params, you could specify them directly inside the array of conditions as Yii2 santizes them.
i have a data array e.g. this:
$data = ['ver_weather' => $post["weathercondition"],
'ver_flash' => $post["flashintense"],
'ver_earth' => $post["earthrumble"]]
these data i use in my sql like this:
$sql = "INSERT INTO `database`.`table` (`weather`, `flash`, `earth`)
VALUES (:ver_weather, :ver_flash, :ver_eart)";
$pdo->prepare($sql)->execute($data);
The result is something like:
INSERT INTO `database`.`table` (`weather`, 'flash', `earth')
VALUES ('1'weather, '1'flash, '1'earth)
So is pdo replacing parts of my keys with the value ?
what is wrong there ?
thanks for helping me out.
edit: Execute does work with named bindings so you could just edit your $data array like this:
$data = [':ver_weather' => $post["weathercondition"],
':ver_flash' => $post["flashintense"],
':ver_earth' => $post["earthrumble"]]
Note the : at the beginning of each key
Original answer below...
I think the issue is that you're trying to bind by name and I don't think PDOStatement supports named bindings. I'd recommend trying the following:
$data = [$post["weathercondition"], $post["flashintense"], $post["earthrumble"]];
$sql = "INSERT INTO `database`.`table` (`weather`, `flash`, `earth`)
VALUES (?, ?, ?)";
$pdo->prepare($sql)->execute($data);
At this specific moment, I want to know how to insert two records into DB. Both are almost the same, except only one single column value changes.
$db = JFactory::getDbo();
$query = $db->getQuery(true);
$columns = array('col1','col2', 'col3', 'col4', 'col5');
$values = array(
$db->quote(A),
$db->quote(x1),
$db->quote(x2),
$db->quote(x3),
$db->quote(x4)
);
$values = array(
$db->quote(B),
$db->quote(x1),
$db->quote(x2),
$db->quote(x3),
$db->quote(x4)
);
...
As you can see, only first value changes. Is there some elegant way to do this?
You code seems to be incomplete since it does not assign your values to the query.
Try this instead. It shows how to add the content of $foo to the column myColumn in the table #__mytable.
$query->insert($db->quoteName('#__mytable'))
->columns('myColumn');
->values(implode(',', array(
$db->quote($foo)
)));
$query->execute();
For multiple values this would help:
foreach($myValues as $myValue) {
$query->values(implode(',', array(
$db->quote($myValue),
)));
}
While there is just one value in my example, it is ready to add multiple columns if needed. Just extend the columns() and values() methods.
My purpose is to update if the value exists, else inserts a new row in the database table after submitting the form.
The problem is, the function here adds new columns in db table instead of updating them.
Here's my function :
MyModel::updateOrCreate(array(
'myField' => 'myValue',
))
->where('myAutoIncrementalField', '=', '5')
->where('myPrimaryKey', '=', '8');
My database table is like that :
1. myPrimaryKey (not auto incremental and is fillable on model.)
2. myAutoIncrementalField (auto incremental and cannot be fillable on model.)
Thank you in advance.
This is how you use this method:
Model::updateOrCreate(
['primary_key' => 8],
['field' => 'value', 'another_field' => 'another value']
);
As 1st param pass an array of fields that are unique, or in your case, the primary key. Non-unique fields don't make sense here obviously just like passing anything along with the PK.
2nd param is an array of values that should be updated/created too, but being ignored in the unique/pk search.
You cannot use where functions with this method. You have to include the where clauses in the array.
MyModel::updateOrCreate(array(
'myField' => 'myValue',
'myAutoIncrementalField' => '5',
'myPrimaryKey' => '8'
));