The user will create an article and submit an image with it.
+The article will go to the articles table.
+The image will go to images table (so that it can be used in other areas of the site).
It has been suggested I use TRANSACTIONS but I am getting errors.
$sql ='BEGIN INSERT INTO articles(article_title, article_text, article_date)
VALUES (?, ?, NOW())
INSERT INTO images(article_id, image_caption)
VALUES(LAST_INSERT_ID(),?);
COMMIT';
$stmt = $conn->stmt_init();
if ($stmt->prepare($sql)) {
$stmt->bind_param('sss', $_POST['article_name'], $_POST['description'], $_POST['image_caption']);
$OK = $stmt->execute();
printf("%d Row inserted.\n", $stmt->affected_rows);
$stmt->free_result();
} else{
echo "Failure- article not uploaded";
}
$mysqli->query("START TRANSACTION");
$stmt = $mysqli->prepare('INSERT INTO articles(article_title, article_text, article_date) VALUES (?, ?, NOW())');
$stmt->bind_param('ss', $_POST['article_name'], $_POST['description']);
$stmt->execute();
$stmt = $mysqli->prepare('INSERT INTO images (article_id, image_caption) VALUES(LAST_INSERT_ID(),?)');
$stmt->bind_param('s', $_POST['image_caption']);
$stmt->execute();
$stmt->close();
$mysqli->query("COMMIT");
It looks like you are using PDO (nice!). With PDO, you can get your transactions in an easy way with beginTransaction() and commit()
Your code would look like:
$pdo->beginTransaction();
// .. fire your 'normal' queries.
// .. and yet some more queries
$pdo->commit();
Then, I'd personally write separate INSERT queries in just two separate statements. More readable in my opinion.
Example:
$pdo->beginTransaction();
$first = $pdo->prepare('INSERT INTO table (field, otherField) VALUES(?,?)');
$second = $pdo->prepare('INSERT INTO table (field, otherField) VALUES(?,?)');
$first->execute(array( .. your data (values) .. ));
$second->execute(array( .. your data (values) .. ));
$pdo->commit();
$sql ='START TRANSACTION;
INSERT INTO articles (article_id,article_title, article_text, article_date) VALUES (NULL,?, ?, NOW());
INSERT INTO images (article_id, image_caption) VALUES(LAST_INSERT_ID(),?);
COMMIT;';
Related
I am pretty new to SQL Transactions and tried to execute following statement which did unfortunately not work...
$stmt = $mysqli->prepare("
BEGIN;
INSERT INTO groups (group_name, group_desc, user_id_fk) VALUES ("'.$groupName.'","'.$groupDesc.'","'.$user_id.'");
INSERT INTO group_users (group_id_fk, user_id_fk) VALUES (LAST_INSERT_ID(), "'.$username.'");
COMMIT;
") or trigger_error($mysqli->error, E_USER_ERROR);
$stmt->execute();
$stmt->close();
Is this even possible what I am trying here or is it completely wrong?
I appreciate every response, thank you!
You are using prepare() wrong way. There is absolutely no point in using prepare() if you are adding variables directly in the query.
This is how your queries have to be executed:
$mysqli->query("BEGIN");
$sql = "INSERT INTO groups (group_name, group_desc, user_id_fk) VALUES (?,?,?)";
$stmt = $mysqli->prepare($sql);
$stmt->bind_param("ssi",$groupName,$groupDesc,$user_id);
$stmt->execute();
$sql = "INSERT INTO group_users (group_id_fk, user_id_fk) VALUES (LAST_INSERT_ID(), ?)";
$stmt = $mysqli->prepare($sql);
$stmt->bind_param("s",$username);
$stmt->execute();
$mysqli->query("COMMIT");
I am in a situation where I need to insert into 2 tables in a query. I've searched around web and could not find solution. What I want to do is insert values in user table & insert values in profile simultaneously. I could do one after the other way but I've read that it is not efficient and is considered as poor coding technique.
Current Code:
$statement = $db->prepare("
BEGIN;
INSERT INTO `user`(`username`, `email`, `password_hashed`, `fname`, `lname`, `dob`, `agreement`, `gender`, `access_token`)
VALUES (?, ?, ?, ?, ?, ?, ?, ?, ?);
INSERT INTO `profile_picture`(`owner`) VALUES (LAST_INSERT_ID());
COMMIT;
");
if($statement) {
$statement->bind_param("ssssssiss", $username, $email, $hashedPassword, $fname, $lname, $dob, $agreement, $gender, $access_token);
$statement->execute();
$statement->close();
echo "DONE";
exit();
}
else printf("Error: %s.\n", $db->error);
I had issues with this trying to copy answers like Frank's. The proper way to do it is:
<?php
try {
$db->beginTransaction();
$stmt = $db->prepare("QUERY");
$stmt->execute();
$stmt = $db->prepare("ANOTHER QUERY??");
$stmt->execute();
$db->commit();
}
catch(PDOException $ex) {
//Something went wrong rollback!
$db->rollBack();
echo $ex->getMessage();
}
After the first statement is executed, you can then gain access to the insertID from PHP using the following: $last_id = $db->lastInsertId();
Hope this helps!
Try using mysqli_multi_query, Check this link for example http://blog.ulf-wendel.de/2011/using-mysql-multiple-statements-with-php-mysqli/
Maybe this one can help you: MySQL Insert into multiple tables?
I think you need a statement like this:
BEGIN;
INSERT INTO user(column_a,column_b) VALUES('value_a','value b');
INSERT INTO profile(column_x,column_y) VALUES('value_x','value_y');
COMMIT;
If you need the last id from user table, you can use the LAST_INSERT_ID() function.
[Updated code from suggestions]
Currently I have two tables in my database. The second table is a junction table for multiple categories from each unique id from the first table. Nothing too special.
Need to accomplish:
I'd like to use two prepared statements where specifically the second statement gets the ID from the first and loops through. Here's what I've tried:
//set autocommit to off
$conn->autocommit(FALSE);
//first table
$stmt1 = $conn->prepare("INSERT INTO birds (db_category, db_class) VALUES (?, ?)");
$stmt1->bind_param('ss',$_POST['db_category'],$_POST['db_class']);
$stmt1->execute();
//get the inserted ID
$lastID = $stmt1->insert_id;
$stmt1->close();
//second table (many to many)
$stmt2 = $conn->prepare("INSERT INTO birdsBiome (birds_id, biomes_id) VALUES (?, ?)");
$arrayValue = $_POST['biomeCheck'];
foreach ($arrayValue as $arrayInsert) {
$stmt2->bind_param('ii', $lastID, $arrayInsert);
$stmt2->execute();
}
$stmt2->close();
//commit both statements
$conn->commit();
$conn->close();
You can access the last insert id as a property of the mysqli object:
$lastID = $conn->insert_id;
Or alternatively you don't have to store $lastID at all if you access it within your SQL:
$stmt2 = $conn->prepare("INSERT INTO birdsBiome (birds_id, biomes_id)
VALUES (LAST_INSERT_ID(), ?)");
By the way, in your code example above you didn't execute $stmt1, so there will be no last insert id anyway.
I have been ripping my hair for days over this problem so any helpful advice would be appreciated. Calling the following function returns nothing. The POST values are set (They print with echo) and the database let me update and extract with other functions. What am i missing?
Oh yea, all the values are strings.
$stmt = $db->prepare("INSERT INTO content_page (name, layout, page_id) VALUES (?,?,?)");
$stmt->bind_param("sss", $_POST['name'], $_POST['layout'], $_POST['page_id']);
$stmt->execute();
$stmt->close();
At glance, there is nothing wrong with this code (in case you are indeed using mysqli). So, the only way to get to know what is going wrong is to get the error message.
Add this line before connect
mysqli_report(MYSQLI_REPORT_ERROR | MYSQLI_REPORT_STRICT);
and make sure you can see PHP errors
Try this
$sql = "INSERT INTO content_page (name, layout, page_id) VALUES (?,?,?)";
if (!$stmt = $db->prepare($sql)) {
die($db->error);
}
$stmt->bind_param("ssi", $_POST['name'], $_POST['layout'], $_POST['page_id']);
if (!$stmt->execute()) {
die($stmt->error);
}
$stmt->close();
Or, if, as you said, all your values are strings (given, they are as well defined as varchars/something similar in your database), you can still bind_param("sss"...
Aren't page_id's integers ? Since the asker first tagged the question as PDO, here is the PDO version :
$stmt = $db->prepare("INSERT INTO content_page (name, layout, page_id) VALUES (:name,:layout,:pid)");
$sth->bindParam(':name', $_POST['name'], PDO::PARAM_STR);
$sth->bindParam(':layout', $_POST['layout'], PDO::PARAM_STR);
$sth->bindParam(':pid', $_POST['page_id'], PDO::PARAM_INT);
$stmt->execute();
Or (MySQLi):
$stmt = $db->prepare("INSERT INTO content_page (name, layout, page_id) VALUES (?,?,?)");
$stmt->bind_param("ssi", $_POST['name'], $_POST['layout'], $_POST['page_id']);
$stmt->execute();
Or (PDO) :
$stmt = $db->prepare("INSERT INTO content_page (name, layout, page_id) VALUES (?,?,?)");
$stmt->execute(array($_POST['name'], $_POST['layout'], $_POST['page_id']));
Here you are:
$name = $_POST['layout'];
$layout = $_POST['layout'];
$page_id= $_POST['page_id'];
$stmt = $db->prepare("INSERT INTO content_page (name, layout, page_id) VALUES ('".$name."','".$layout."','".$page_id."')");
I'm trying to insert data from a form into a database using PHP and Mysqli but I can't get it working! My database has 4 fields: DATE, TITLE, CONTENT, ID. The ID field is auto-increment.
I've checked the connection and that's working fine. I've also echoed the form field values and the $blogDate variable I created, they're all fine too.
Here's my prepared statement:
if ($newBlog = $mysqli->prepare('INSERT INTO Blog VALUES ($blogDate, $_POST["bTitle"], $_POST["bContent"])')) {
$newBlog->execute();
$newBlog->close();
}
It's just not inserting the values into my table.
You are generating SQL containing strings that are not quoted or escaped.
Don't insert the data directly into the SQL string, use placeholders (?) and then bind the parameters before executing.
$query = "INSERT INTO Blog VALUES (?, ?, ?)";
$stmt = $mysqli->prepare($query);
$stmt->bind_param("sss", $blogDate, $_POST["bTitle"], $_POST["bContent"]);
$stmt->execute();
Since you are aware about prepared statement:
$newBlog = $mysqli->prepare('INSERT INTO Blog (`dateCol`, `titleCol`, `contentCol`) VALUES (?, ?, ?)');
$newBlog->bind_param( 'sss', $blogDate, $_POST["bTitle"], $_POST["bContent"] );
$newBlog->execute();
$newBlog->close();
since you are using auto increment field you need to specify column name and then values
try this code
$query = "INSERT INTO Blog (colname_1,colname_2,colname_3) VALUES (?, ?, ?)";
$stmt = $mysqli->prepare($query);
$stmt->bind_param("sss", $blogDate, $_POST["bTitle"], $_POST["bContent"]);
$stmt->execute();