MySQL INSERT Fatal -> 'PDOException' with message 'SQLSTATE[42000]: - php

I have a function that does an INSERT:
function insertData($data){
global $dbh;
$sql = sprintf(
"INSERT INTO location " .
"(" .
"data1, " .
"data2, " .
"data3" .
") " .
"VALUES ('%s', '%s', '%s')",
$data['data1'],
$data['data2'],
$data['data3']
);
echo "$sql \n";
$adjusted = $dbh->quote($sql);
$stmt = $dbh->prepare($adjusted);
$stmt->execute();
$lastId = $dbh->lastInsertId();
return $lastId;
}
When the function is called, I get this error:
INSERT INTO location (data1, data2, data3) VALUES ('Blah1', 'Blah2', 'Blah3')
Fatal error: Uncaught exception 'PDOException' with message 'SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ''INSERT INTO location (data1, data2, data3) VALUES (\'Bl' at line 1' in /var/www/test/lib/saveData.php:59
Stack trace:
#0 /var/www/test/lib/saveData.php(59): PDO->prepare(''INSERT INTO lo...')
#1 /var/www/test/lib/saveData.php(10): insertData(Array)
If I run the insert directly it works fine.
I can't figure out what PDO does not like about my syntax.
UPDATE:
Is there a significant difference between using the paramaterization
$sql = "INSERT INTO location (data1, data2, data3) VALUES (?, ?, ?)";
or
$sql = "INSERT INTO location (data1, data2, data3) VALUES (:data1, :data2, :data3)";
UPDATE 2
function insertData($data){
global $dbh;
$sql = "INSERT INTO location " .
"(" .
"data1, " .
"data2, " .
"data3, " .
"data4" .
") VALUES (?, ?, ?, ?)";
$stmt = $dbh->prepare($sql);
$stmt->execute($data);
$lastId = $dbh->lastInsertId();
return $lastId;
}
UPDATE 3 - A debrief For the sake of other readers
I was being clever with sprintf() based on an example I picked up somewhere.
Using sprintf() to build the sql statement is not the same as using named or anonymous bind parameters, so I used the '?' bind parameter and everything worked fine.
Also, I am stuck building on an old system for now, so the shorthand [] array notation was also interfering with successful completion of the task.
Thanks for the input to those who responded.

You are not preparing your statement correctly. sprtinf and quote are breaking your query. Get rid of them and pass the values to execute
function insertData($data) {
global $dbh;
$sql = 'INSERT INTO location
(
data1,
data2,
data3
) VALUES (:data1, :data2, :data3)';
$stmt = $dbh->prepare($sql);
$stmt->execute(array(
'data1' => $data['data1'],
'data2' => $data['data2'],
'data3' => $data['data3']
));
$lastId = $dbh->lastInsertId();
return $lastId;
}
Update:
I have added named placeholders, but I am still building the array manually. If you are sure that $data contains exactly the number of items matching your placeholders you can pass it in directly to execute.

Related

My SQL statment is correct but still returns an error

On my website I try to take a few info and add them to my database but ever since I changed the date to datetime the whole SQL statment doesn't work anymore.
I looked everywhere online and no one else seem to have the same problem I might just have missed something but the SQL statment looks correct to me.
public function addTimeLine($typeOfPost,$post,$idImage,$numberImage){
$post = addslashes($post);
$typeOfPost = addslashes($typeOfPost);
$date = date("Y-m-d H:i:s");
$query = "INSERT INTO `time_line` ( `special_note`, `type`, `id_image`, `number_image`, `dates`) VALUES ( '".$post."', '".$typeOfPost."', ".$idImage.", ".$numberImage.", '".$date."')";
$ps = $this->_db->prepare($query);
$ps->execute();
}
and it gives me this error
Fatal error: Uncaught PDOException: SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ' 1, '2019-07-12 16:29:58')' at line 1
Your not using prepared statements correctly. You need to use placeholders and then pass the values in the execute
public function addTimeLine($typeOfPost, $post, $idImage, $numberImage) {
$date = date("Y-m-d H:i:s");
$query = "INSERT INTO `time_line` ( `special_note`, `type`, `id_image`, `number_image`, `dates`) VALUES ( ?, ?, ?, ?, NOW())";
$ps = $this->_db->prepare($query);
$ps->execute([
$post,
$typeOfPost,
$idImage,
$numberImage
]);
}
You're missing quotes, try the following:
$query = "INSERT INTO time_line(`special_note`, `type`, `id_image`, `number_image`, `dates`) VALUES ({$post},{$typeOfPost},{$idImage},{$numberImage},{$date})";

insert...on duplicate key update does not work with php, but works directly on MySQL

$sql = "SET #tag_name = '$tag_value',
#tag_link = '$tag_link',
#user_value = '$user_value';
INSERT INTO urls_unis
(tag_name, tag_link, user_data)
VALUES
(#tag_name, #tag_link, #user_value)
ON DUPLICATE KEY UPDATE
tag_name = #tag_name,
tag_link = #tag_link,
user_data = #user_value;
";
if(mysqli_query($link, $sql)){
echo "Records inserted successfully.";
} else{
echo "ERROR: Could not able to execute $sql. " . mysqli_error($link);
}
}
The above code is returning this:
ERROR: Could not able to execute
SET #tag_name = 'View history', #tag_link = 'zNIL', #user_value = '/w/index.php?title=Non-volatile_random-access_memory&action=history'; INSERT INTO urls_unis (tag_name, tag_link, user_data) VALUES (#tag_name, #tag_link, #user_value) ON DUPLICATE KEY UPDATE tag_name = #tag_name, tag_link = #tag_link, user_data = #user_value; .
You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'INSERT INTO urls_unis (tag_name, tag_link, user_data) VALUES (#tag_name,' at line 4
When I copy and paste the mysql query to phpmyadmin to execute it, it works fine. No errors were returned.
How come, and how can I solve this?
You can't run multiple querylines in a single query. You need to run them separately or use mysqli_multi_query(). You can avoid all that by just using your variables, without going through the route of setting the MySQL variables first.
Better yet, you would use a prepared statement instead of injecting your variables directly into the query. Because you're using the values twice, and that MySQLi doesn't support named placeholders, we have to bind each variable twice.
$sql = "INSERT INTO urls_unis (tag_name, tag_link, user_data)
VALUES
(?, ?, ?)
ON DUPLICATE KEY UPDATE
tag_name = ?,
tag_link = ?,
user_data = ?;";
$stmt = $link->prepare($sql);
$stmt->bind_param("ssssss", $tag_value, $tag_link, $user_value,
$tag_value, $tag_link, $user_value);
if ($stmt->execute()){
echo "Records inserted successfully.";
} else{
echo "ERROR: Could not able to execute $sql<br />";
echo $stmt->error;
}
$stmt->close();
When should I use prepared statements?

PHP PDO SQL syntax error [duplicate]

This question already has an answer here:
Syntax error due to using a reserved word as a table or column name in MySQL
(1 answer)
Closed 6 years ago.
I've looked around the internet and haven't been able to resolve this issue.
I'm trying to insert a row into a mySQL table using PDO through this function
function newItem($name, $desc, $price, $catID){
echo $name . "\n";
echo $price . "\n";
echo $desc . "\n";
echo $catID . "\n";
$conn = self::connect();
//INSERT Order
$sql = "INSERT INTO catalogue (Name, Price, CatID, Desc)
VALUES ('$name', $price, $catID, '$desc')";
// use exec() because no results are returned
$conn->exec($sql);
}
when i do, i get this error:
Fatal error: Uncaught exception 'PDOException' with message 'SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'Desc) VALUES ('User', 0.00, 3, 'theUser')' at line 1' in C:\xampp\htdocs\classes\catalogue.php:65 Stack trace: #0 C:\xampp\htdocs\classes\catalogue.php(65): PDO->exec('INSERT INTO cat...') #1 C:\xampp\htdocs\classes\main.php(39): Catalogue->newItem('User', 'theUser', '0.00', '3') #2 {main} thrown in C:\xampp\htdocs\classes\catalogue.php on line 65
I can confirm that the self::connect(); method works, and the problem only occurs when i try to insert data into the Desc column.
I've spent a good while trying to sort this issue, however my knowledge of PDO is quite vague....
Can anyone see where I've gone wrong?
the echo's show this:
User 0.00 theUser 3
DESC is a keyword. You have to escape the column Name using backtics or better rename the column.
$sql = "INSERT INTO catalogue (Name, Price, CatID, `Desc`)
VALUES ('$name', $price, $catID, '$desc')";
For more Information about keywords see the official documentation.
Desc is reserved keyword in mysql in must be in backtick https://dev.mysql.com/doc/refman/5.7/en/keywords.html.html and use prepare and bind statement
$sth = $conn->prepare("INSERT INTO catalogue (Name, Price, CatID, `Desc`)
VALUES (:Name, :Price, :CatID, :Desc)");
$sth->bindParam(':Name', $name, PDO::PARAM_STR);
$sth->bindParam(':Price', $price, PDO::PARAM_STR);
$sth->bindParam(':CatID', $catID, PDO::PARAM_INT);
$sth->bindParam(':Desc', $desc, PDO::PARAM_STR);
$sth->execute();
Try this
$sql = "INSERT INTO catalogue (Name, Price, CatID, Desc)
VALUES ('".$name."', $price, $catID, '".$desc."')";

MYSQL Syntax error in php but sql is valid

I'm trying to start a transaction is mysql and insert data into the database. The database source sql can be found on github here. Here is the error:
Error: START TRANSACTION; INSERT INTO Books(Title, PublicationDate,
PurchaseDate, Description, LocationID, GenreID) VALUES('Simple
Genius', '2008-4-1','2009-5-7','','Hardbook Library','Fiction'); SET
#bookid = LAST_INSERT_ID(); INSERT INTO BookAuthors(FirstName,
MiddleName, LastName) VALUES('David', '', 'Baldacci'); SET #authorid =
LAST_INSERT_ID(); INSERT INTO AuthorsInBooks(AuthorID, BookID)
VALUES(#authorid, #bookid); COMMIT; You have an error in your SQL
syntax; check the manual that corresponds to your MySQL server version
for the right syntax to use near 'INSERT INTO Books(Title,
PublicationDate, PurchaseDate, Description, LocationID,' at line 3
Near 'INSERT INTO Books(Title, PublicationDate, PurchaseDate, Description, LocationID,' doesn't make sense to me because it is missing GenreID after LocationID. Am i missing something? When I copy and paste this code into phpmyadmin it works fine. My php version is 5.4.
Here is php code:
$sql = "
START TRANSACTION;
INSERT INTO Books(Title, PublicationDate, PurchaseDate, Description, LocationID, GenreID)
VALUES('".$Title."', '".$YearWritten."','".$YearPurchased."','".$Description."','".$Location."','".$Genre."');
SET #bookid = LAST_INSERT_ID();
INSERT INTO BookAuthors(FirstName, MiddleName, LastName)
VALUES('".$AuthFirstName."', '".$AuthMiddleName."', '".$AuthLastName."');
SET #authorid = LAST_INSERT_ID();
INSERT INTO AuthorsInBooks(AuthorID, BookID)
VALUES(#authorid, #bookid);
COMMIT;
";
if (mysqli_query($conn, $sql)) {
echo "New record created successfully";
} else {
echo "Error: " . $sql . "<br>" . mysqli_error($conn);
}
mysqli_close($conn);
mysqli_query() can only execute 1 query, if you want to execute multiple queries, you need:
if (mysqli_multi_query($conn, $sql)) {
In response to your comment "Can I see an example of what you mean #eggyal ?":
// mysqli provides API calls for managing transactions
mysqli_autocommit($conn, false);
// parameterise variables - NEVER concatenate them into dynamic SQL
$insert_book = mysqli_prepare($conn, '
INSERT INTO Books
(Title, PublicationDate, PurchaseDate, Description, LocationID, GenreID)
VALUES
(?, ?, ?, ?, ?, ?)
');
// bind the variables that (will) hold the actual values
mysqli_stmt_bind_param(
$insert_book,
'siisss', // string, integer, integer, string, string, string
$Title, $YearWritten, $YearPurchased, $Description, $Location, $Genre
);
// execute the statement (you can change the values of some variables and
// execute repeatedly without repreparing, if so desired - much faster)
mysqli_stmt_execute($insert_book);
// mysqli provides API calls for obtaining generated ids of inserted records
$book_id = mysqli_insert_id($conn);
// ... etc ...
// use the API call to commit your transaction
mysqli_commit($conn);
// tidy up
mysqli_stmt_close($insert_book);
Note that I've not included above any error detection/handling, which you'd certainly want to include in any real-world code.

Error: You have an error in your SQL syntax; near ')' at line 1

Im having a problem with my PHP code, it says the error is "Error: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ')' at line 1"
It connects to the database ok as it echos "Database Connection Successful" but it dosnt insert the data into the database. This worked fine before, but now all of a sudden its stopped working. Can anyone help?
<?php
$username = "student";
$password = "student";
$hostname = "localhost";
$db = "details";
$link = new mysqli($hostname, $username, $password, $db);
if ($link->connect_errno)
printf("Connect failed: %s\n", $link->connect_error);
else
echo "Database Connection Successful \n";
echo nl2br("\n");
$Urgency = "Urgency";
if(isset($_POST['submit'])){
$TypeOfProblem = $_POST['problemtype'];
$ProblemDescription = $_POST['problem'];
$RoomNo = $_POST['roomno'];
$Problem = $_POST['reporter'];
$Urgency = $_POST['Urgency'];
$Date = $_POST['date'];
//Insert into Database
$sql = "INSERT INTO `details`.`problem` (`Type Of Problem`, `Problem Description`, `RoomNo`, `Urgency`, `UserIDProblem`,`Date` ) VALUES ('$TypeOfProblem', '$ProblemDescription', '$RoomNo', '$Urgency', '$Problem', $Date)";
if (!mysqli_query($link, $sql))
{
die('Error: ' . mysqli_error($link));
}
echo "\n Thank you. Your Helpdesk Call has been submitted.";
mysqli_close($link);
}//////// end isset submit if ////////
?>
Thanks
Try using this, the problem is the single quote ` should be '
$sql = "INSERT INTO 'details'.'problem' ('Type Of Problem', 'Problem Description', 'RoomNo', 'Urgency', 'UserIDProblem','Date' ) VALUES ('$TypeOfProblem', '$ProblemDescription', '$RoomNo', '$Urgency', '$Problem', '$Date')"
Or try to set an echo $sql and test the query directly on de dbms
The date '$Problem', $Date)"; needs single-quotes '$Problem', '$Date')";
First, it is a good idea to leave out the database name:
$sql = "INSERT INTO `problem` (`Type Of Problem`, `Problem Description`, `RoomNo`, `Urgency`, `UserIDProblem`, `Date`) VALUES ('$TypeOfProblem', '$ProblemDescription', '$RoomNo', '$Urgency', '$Problem', $Date)";
Are you sure, that your column names have spaces in it? I mean this would work, but this is not a good idea, I think.
I cannot find another problem in your query, maybe you should quote the date:
$sql = "INSERT INTO `problem` (`Type Of Problem`, `Problem Description`, `RoomNo`, `Urgency`, `UserIDProblem`, `Date`) VALUES ('$TypeOfProblem', '$ProblemDescription', '$RoomNo', '$Urgency', '$Problem', '$Date')";
Otherwise, please provide us with the full query:
die("INSERT INTO `problem` (`Type Of Problem`, `Problem Description`, `RoomNo`, `Urgency`, `UserIDProblem`, `Date`) VALUES ('$TypeOfProblem', '$ProblemDescription', '$RoomNo', '$Urgency', '$Problem', $Date)");
And you SHOULD notice, that your code is exploitable with SQL-Injections! Use mysqli_real_escape_string.
For debugging this, output the actual SQL text that is being submitted to the database, using echo or vardump e.g.
$sql = "INSERT INTO ...";
echo "SQL=" . $sql ;
That will show you the actual statement that's going to be submitted to the database, and you can usually debug the problem from there.
If date isn't a numeric, if it represents a DATE datatype or a string, the value needs to be enclosed in single quotes. Otherwise, it's likely going to be interpreted in a numeric context.
Note that this code appears to be vulnerable to SQL Injection, because it includes potentially unsafe values in the SQL text. Consider what happens when a value contains "special" characters, like a single quote, or comma.
Potentially unsafe values must be properly escaped. With mysqli, you can use the mysqli_real_escape_string function.
A better pattern is to use a prepared statement with bind placeholders.
As an example of what that would look like (before it's cluttered up with code to checks for errors from the return of the mysqli_ function calls)
$sql = "INSERT INTO `details`.`problem`
(`Type Of Problem`,`Problem Description`,`RoomNo`,`Urgency`,`UserIDProblem`,`Date`)
VALUES (?,?,?,?,?,?)";
$sth = mysqli_prepare($link,$sql);
if (!$sth) {
echo "error:" . mysqli_error($link);
)
mysqli_stmt_bind_param($sth,"ssssss"
,$TypeOfProblem,$ProblemDescription,$RoomNo,$Urgency,$Problem,$Date);
mysqli_stmt_execute($sth);

Categories