Inserting into two tables with one query - c#

What's wrong with my code, i tried to combine two query into one. But the second query is not working, i already follow the answer of this link INSERT INTO two tables at one query but i think mine doesn't work, am i missing something in my code?
string sql = "INSERT INTO tbladdbook(fBookTitle,fAuthor,fBookYr,fEdition,fPublication,fAccNo,fCallNo,fCategory,fBarCodeNo,fCurrentCopies) VALUES('"
+ txtTITLE.Text + "','"
+ txTAUTHOR.Text + "','"
+ txtBOOKYR.Text + "','"
+ txtEDITION.Text + "','"
+ txtPUBLICATION.Text + "','"
+ txtACCESSNO.Text + "','"
+ txtCALLNO.Text + "','"
+ txtCATEGORY.SelectedItem + "','"
+ txtBARCODE.Text + "','"
+ txtCOPIES.Text + "'); INSERT INTO tbltruecopies(fBookTitle,fAuthor,fBarCodeNo,fTrueCopies) VALUES('"
+ txtTITLE.Text + "','"
+ txTAUTHOR.Text + "','"
+ txtBARCODE.Text + "','"
+ txtCOPIES.Text + "')";
cfgotcall.inputQ(sql);
Table definition: for tbladdbook
fBookTitle varchar
fAuthor varchar
fEdition varchar
fBookYr varchar
fPublication varchar
fAccNo varchar
fCallNo varchar
fCategory varchar
fBarCodeNo varchar
fCurrentCopies float
Table definition: for tbltrue
fBookTitle varchar
fAuthor varchar
fBarCodeNo bigint
fTrueCopies bigint
Old and working code:
string sql = "INSERT INTO tbladdbook(fBookTitle,fAuthor,fBookYr,fEdition,fPublication,fAccNo,fCallNo,fCategory,fBarCodeNo,fCurrentCopies) VALUES('"
+ txtTITLE.Text + "','"
+ txTAUTHOR.Text + "','"
+ txtBOOKYR.Text + "','"
+ txtEDITION.Text + "','"
+ txtPUBLICATION.Text + "','"
+ txtACCESSNO.Text + "','"
+ txtCALLNO.Text + "','"
+ txtCATEGORY.SelectedItem + "','"
+ txtBARCODE.Text + "','"
+ txtCOPIES.Text + "')";
cfgotcall.inputQ(sql);
sql = "INSERT INTO tbltruecopies(fBookTitle,fAuthor,fBarCodeNo,fTrueCopies) VALUES('"
+ txtTITLE.Text + "','"
+ txTAUTHOR.Text + "','"
+ txtBARCODE.Text + "','"
+ txtCOPIES.Text + "')";
cfgotcall.inputQ(sql);

Captain Teemo asked if I was able to rewrite using parameters.
This is a relatively easy operation; however, I write for SQL Server and there may be slight differences with the MySql commands and I do not the cfgotcall methods (is this Cold Fusion?) that are being used for the Data Layer, so I will just write this in ADO.
In this case I simply replaced all of the values in the VALUES clause with SQL Variables, and basically reused the column names with a preceding #, so the column fBookTitle is assigned the value #fBookTitle. Then we can assign those parameters to the command object via the Parameters.AddWithValue() method. For the above #fBookTitle value the call would be cmd.Parameters.AddWithValue("#Title", txtTITLE.Text); I noticed that the variables being used in the second query were all in the first query, but not vice versa; so I am going to build up execute Qry2 first, then we can simply change the CommandText and add in the additional parameters.
One of the things with using parameters is that you will need to add the values with the correct type, so adding in a value that is a BigInt in the database will need to be added in as the corresponding C# type of Int64.
What I can do is show how this would be done via ADO with SQL Server, and you can modify what needs to be done. If you can't find a cfgotcall that works with parameters then you could just change this for use with MySql which has nearly identical syntax to the SQL Server syntax.
string Qry1 = "INSERT INTO tbladdbook(fBookTitle,fAuthor,fBookYr,fEdition,fPublication,fAccNo,fCallNo,fCategory,fBarCodeNo,fCurrentCopies) VALUES (#Title, #Author, #BookYr, #Edition, #Publication, #AccNo, #CallNo, #Category, #BarCode, #Copies)";
string Qry2 = "INSERT INTO tbltruecopies(fBookTitle, fAuthor, fBarCodeNo, fTrueCopies) VALUES (#Title, #Author, #Barcode, #Copies)";
using (SqlConnection conn = new SqlConnection(connectionstring)) {
conn.Open();
using (SqlCommand cmd = new SqlCommand()) {
cmd.Connection = conn;
cmd.CommandType = CommandType.Text;
cmd.CommandText = Qry2;
cmd.Parameters.AddWithValue("#Title", txtTITLE.Text);
cmd.Parameters.AddWithValue("#Author", txTAUTHOR.Text);
cmd.Parameters.AddWithValue("#Barcode", Int64.parse(txtBARCODE.Text));
cmd.Parameters.AddWithValue("#Copies", Int64.parse(txtCOPIES.Text));
try { cmd.ExecuteNonQuery(); }
catch (Exception) { /* your error handling */ }
cmd.CommandText = Qry1;
cmd.Parameters.AddWithValue("#BookYr", txtBOOKYR.Text);
cmd.Parameters.AddWithValue("#Edition", txtEDITION.Text);
cmd.Parameters.AddWithValue("#Publication", txtPUBLICATION.Text);
cmd.Parameters.AddWithValue("#AccNo", txtACCESSNO.Text);
cmd.Parameters.AddWithValue("#CallNo", txtCALLNO.Text);
cmd.Parameters.AddWithValue("#Category", txtCATEGORY.SelectedItem);
try { cmd.ExecuteNonQuery(); }
catch (Exception) { /* your error handling */ }
}
conn.Close();
}
Tetsuya Yamamoto suggests that this be converted over to a Stored Procedure
This is an easy enough task on SQL Server, but I do not know the MySql implementation; sorry you are going to get what I would be typing in Query Analyzer or SSMS, and this would most likely to be translated for MySql as well.
The syntax for this procedure is going to be rather simple, as all we are going to do is wrap the 2 queries within it.
CREATE PROCEDURE usp_addBookAndCopies (
#Title VARCHAR(100),
#Author VARCHAR(100),
#BookYr VARCHAR(100),
#Edition VARCHAR(100),
#Publication VARCHAR(100),
#AccNo VARCHAR(100),
#CallNo VARCHAR(100),
#Category VARCHAR(100),
#BarCode BIGINT,
#Copies BIGINT
) AS
BEGIN
INSERT tbladdbook ( fBookTitle, fAuthor, fBookYr, fEdition, fPublication,
fAccNo, fCallNo, fCategory, fBarCodeNo, fCurrentCopies )
VALUES (#Title, #Author, #BookYr, #Edition, #Publication,
#AccNo, #CallNo, #Category, #BarCode, #Copies )
INSERT tbltruecopies ( fBookTitle, fAuthor, fBarCodeNo, fTrueCopies)
VALUES (#Title, #Author, #Barcode, #Copies)
END
GO
Once we have the Stored Procedure created, we would need to modify the original code, removing the 2 INSERT queries and replace them with the one command calling the procedure. We would also change the command type to reflect that we are running a procedure instead of a text command.
// Not Needed: string Qry1 = "INSERT INTO tbladdbook..."
// Not Needed: string Qry2 = "INSERT INTO tbltruecopies..."
using (SqlConnection conn = new SqlConnection(connectionstring)) {
conn.Open();
using (SqlCommand cmd = new SqlCommand()) {
cmd.Connection = conn;
cmd.CommandType = CommandType.StoredProcedure; // Changed
cmd.CommandText = "usp_addBookAndCopies"; // Changed
cmd.Parameters.AddWithValue("#Title", txtTITLE.Text);
cmd.Parameters.AddWithValue("#Author", txTAUTHOR.Text);
cmd.Parameters.AddWithValue("#Barcode", Int64.parse(txtBARCODE.Text));
cmd.Parameters.AddWithValue("#Copies", Int64.parse(txtCOPIES.Text));
cmd.Parameters.AddWithValue("#BookYr", txtBOOKYR.Text);
cmd.Parameters.AddWithValue("#Edition", txtEDITION.Text);
cmd.Parameters.AddWithValue("#Publication", txtPUBLICATION.Text);
cmd.Parameters.AddWithValue("#AccNo", txtACCESSNO.Text);
cmd.Parameters.AddWithValue("#CallNo", txtCALLNO.Text);
cmd.Parameters.AddWithValue("#Category", txtCATEGORY.SelectedItem);
try { cmd.ExecuteNonQuery(); }
catch (Exception) { /* your error handling */ }
}
conn.Close();
}
My Comments
Looking at the actual statements and the code this appears to be adding books to a library of sorts. There is a table of Books (tbladdbook) and another for Book Copies (tbltruecopies), and the only thing different between the two tables is that Copies would reflect how many copies are currently on hand, but the Count is of dissimilar types; one being Float and the other as BigInt. My opinion would be that these two should be of the same type, and I really don't think it is realistic that these values would ever exceed the capacity of a 32 bit integer, if not 16 bit. Not too mention that Float and Double are only approximations.
This a rather long answer, and my aging eyes may have a syntax error or two. Please forgive me and let me know of any errors or suggestions, I will be happy to update this for you.

Related

Error in MySQL synax inserting new data c#

I think its one of those question where you need a second pair of eyes to have a look at.
I trying to add new record and just keep getting same error which is "Error in SQL syntax , I am using MySQL and here is the table
script for MySQL
create table tbl_employee(
employeeID smallint,
employee_Fname varchar(30),
employee_Sname varchar(30),
employee_AddressL1 varchar(100),
employee_AddressL2 varchar(100),
employee_PostCode varchar(10),
employee_tel_type enum('work', 'mobile', 'personal'),
employee_Image varchar(250),
employee_Job_Role enum('admin','accounts','management','maintiantance','Sales'),
employee_Salary float,
employee_imagePath varchar(250),
employee_tel_no varchar(100),
Primary key(employeeID)
);
and here is the C# code
connected = DataConnection.getConn();
MySqlCommand cmd = new MySqlCommand("", connected); //
//This is my insert query in which i am taking input from the user through windows forms
//insert into tbl_employee value (2,'John','Rafiq','234 Zoo Rd','Alcala','2388','work' ,'admin',3500.89,'C:\blindXimages','111-111' );
string Query = "Insert into tbl_employee (employeeID,employee_fname,employee_Sname,employee_AddressL1,employee_AddressL2,employee_PostCode, employee_tel_type,employee_Job_Role,employee_Salary,employee_ImagePath,employee_tel_no)" +
"'value('" + Convert.ToInt32( this.txtEmployeeID.Text) + "'," + this.txtName.Text + "','" + this.txtSurname.Text + "','" + this.txtAddressL1.Text + "','" + this.txtAddressL2.Text + "','" + this.txtPostCode.Text + "','" + this.txtTelType.Text + "','" + this.txtJobRole.Text + "','" + Convert.ToDecimal( this.txtSalary.Text) + "','" + this.txtFaceName.Text + "','" + this.txtTelephoneNo.Text + "')";
//This is command class which will handle the query and connection object.
MySqlCommand MyCommand2 = new MySqlCommand(Query, connected);
MySqlDataReader MyReader2;
MyReader2 = MyCommand2.ExecuteReader(); // Here our query will be executed and data saved into the database.
MessageBox.Show("Save Data");
while (MyReader2.Read())
{
}
// connected.Close();
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
btnAddNew.Enabled = false;
MessageBox.Show("Data is save clearing all text boxes ");
clearTextBox();
}
I have double and triple check my syntax just can't figure out were I am going wrong line by line. will very much appropriate this support.
use "values" instead of "value" and add space before values.

How to convert DateTimepicker value to date datatype?

My database is:
create table bus
( bus_no varchar(10),
jdate date,
source varchar(20),
destination varchar(20),
departtime varchar(10),
primary key(bus_no,jdate));
C#
c.connect();
comm = new OracleCommand(); /*Class OracleCommand represents an SQL statement or stored procedure to execute against a database. OracleCommand() initializes a new instance of the OracleCommand. */
comm.Connection = c.conn;
//Console.Write(dateTimePicker1.Value.ToShortDateString());
comm.CommandText = "INSERT INTO bus VALUES ('" + busno.Text + "','" + dateTimePicker1.Value.ToShortDateString() + "','" + source.Text + "','" + destination.Text + "','" + departtime.Text + "')";
comm.CommandType = CommandType.Text;
MessageBox.Show("Bus Added");
comm.ExecuteNonQuery();
c.conn.Close();
It's showing error as month is not recognized. Please help.
you can use custom formatter to format it to correct format. Generally default short string of C# not work with Oracle.
dateTimePicker1.Value.ToString("MM/dd/yyyy")
or
dateTimePicker1.Value.ToString("M/d/yyyy")
You should never use concatenated SQL strings in your applications. Parameterized queries will be faster and help you to avoid SQL Injection and troubles with type conversion.
c.connect();
comm = new OracleCommand(); /*Class OracleCommand represents an SQL statement or stored procedure to execute against a database. OracleCommand() initializes a new instance of the OracleCommand. */
comm.Connection = c.conn;
comm.CommandText = "INSERT INTO bus VALUES (:bus_no, :jdate, :source, :destination, :departtime)";
comm.Parameters.Add("bus_no", busno.Text);
comm.Parameters.Add("jdate", dateTimePicker1.Value);
comm.Parameters.Add("source", source.Text);
comm.Parameters.Add("destination", destination.Text);
comm.Parameters.Add("departtime", departtime.Text);
comm.ExecuteNonQuery();
MessageBox.Show("Bus Added");
c.conn.Close();

Error SQL INSERT INTO with Odbc Command C#

Scenario:
I want to input data from textbox into the database based on microsoft data base (.mdb)
I already searching and find good clue and my result was here.
This Code below was inside command button click event:
using (OdbcConnection conn= new OdbcConnection())
{
conn.ConnectionString = #"Driver={Microsoft Access Driver (*.mdb)};" +
"Dbq=C:\\BlaBlaBla.mdb;Uid=Admin;Pwd=;";
conn.Open();
using (OdbcCommand cmd = new OdbcCommand(
"INSERT INTO TABLENAME (FIELD1,FIELD2,FIELD3) VALUES ('" + txtFIELD1Input.Text + "','" + txtFIELD2Input.Text + "','" + txtFIELDInput.Text + "' )", conn))
{
cmd.ExecuteNonQuery();
}
conn.Close();
}
And when I click the command button, I get unfriendly exception
ERROR [42S02] [Microsoft][ODBC Microsoft Access Driver] Could not find
output table 'TABLENAME'.
That happened when I insert cmd.ExecuteNonQuery. If I didn't insert that, of course nothing happens in my table target.
So what mistakes did I make in that code? What should I do?
"INSERT INTO TABLENAME (FIELD1,FIELD2,FIELD3) VALUES ('" + txtFIELD1Input.Text + "','" + txtFIELD2Input.Text + "','" + txtFIELDInput.Text + "' )", myConnection))
change this into
"INSERT INTO TABLENAME (FIELD1,FIELD2,FIELD3) VALUES ('" + txtFIELD1Input.Text + "','" + txtFIELD2Input.Text + "','" + txtFIELDInput.Text + "' )", Conn))
you define Conn as your connection string not "myConnection"
So i changed to OleDbConnection And My Problem Cleared,
using (OleDbConnectionconn= new OleDbConnection())
{
conn.ConnectionString = #"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=C:\Users\LOSERONE\Documents\DATABASE\Latihan1.mdb";
conn.Open();
using (OleDbCommand cmd = new OleDbCommand (
"INSERT INTO TABLENAME (FIELD1,FIELD2,FIELD3) VALUES ('" + txtFIELD1Input.Text + "','" + txtFIELD2Input.Text + "','" + txtFIELDInput.Text + "' )", conn))
{
cmd.ExecuteNonQuery();
}
conn.Close();
}
Seems, to connected the database must same as the connection string in the properties on the targeted database.
Does anyone can tell me what is the difference OleDbConnection with OdbcConnection in .mdb database file?!
This problem is because sql connection's default database after login is not the same where your table 'TABLENAME' exists. Try to add database name before table like this:
INSERT INTO DBNAME..TABLENAME (FIELD1, FIELD2)
replace your myConnection to Conn

How to execute 2 Sql statements with one button click

I've managed to run this query using wamp.
INSERT INTO guest (guestno,familyname)
VALUES(NULL,'Damn');
INSERT INTO reservation (reservationno, guestno)
VALUES(NUll,LAST_INSERT_ID())
However If I separately execute these 2 insert statements I will have a foreign key constraint.
I think the both of them need to be executed at the same time.
My questions are:
How to incorporate this into my c# winform code?
Is it possible to have 2 insert statements on one button?
When the user presses "add reservation" I would like the two MySQl query's to be executed.
Here's my insert statement:
private void button7_Click(object sender, EventArgs e)
{
string connectionString =
"Server=localhost;" +
"Database=sad;" +
"User ID=root;" +
"Password=root;" +
"Pooling=false";
IDbConnection dbcon;
dbcon = new MySqlConnection(connectionString);
dbcon.Open();
IDbCommand dbcmd = dbcon.CreateCommand();
string sql = "<insert statement>";
dbcmd.CommandText = sql;
IDataReader reader = dbcmd.ExecuteReader();
reader.Read();
}
UPDATED VERSION (DOESN'T WORK)
string connectionString =
"Server=localhost;" +
"Database=sad;" +
"User ID=root;" +
"Password=root;" +
"Pooling=false";
Form3 f3 = new Form3();
IDbConnection dbcon;
dbcon = new MySqlConnection(connectionString);
dbcon.Open();
IDbCommand dbcmd = dbcon.CreateCommand();
string sql = "insert into guest (guestno, familyname) values (null, '" + textBox6.Text + "'); insert into reservation (reservationno, guestno) values (null, LAST_INSERT_ID())";
dbcmd.CommandText = sql;
IDataReader reader = dbcmd.ExecuteReader();
reader.Read();
MessageBox.Show("Added Guest Reservation Successfully");
f3.guestList();
f3.reservationList();
Updated No.3 (STILL DOESN'T WORK)
string connectionString =
"Server=localhost;" +
"Database=sad;" +
"User ID=root;" +
"Password=root;" +
"Pooling=false";
IDbConnection dbcon;
dbcon = new MySqlConnection(connectionString);
dbcon.Open();
IDbCommand dbcmd = dbcon.CreateCommand();
dbcmd = new MySqlCommand("CreateGuestAndReservation", dbcon);
dbcmd.CommandType = CommandType.StoredProcedure;
dbcmd.Parameters.AddWithValue("familyName", "foo");
dbcmd.ExecuteNonQuery();
enter code here
You can't execute more than one statement on a given MySqlCommand.
Your best bet all around (maintainability, performance, readability) is to:
create a MySQL stored procedure for your 2 SQL statements.
call your stored proc using ExecuteNonQuery().
DELIMITER //
CREATE PROCEDURE CreateGuestAndReservation
(
IN familyName VARCHAR(255)
)
BEGIN
insert into guest (guestno, familyname)
values (null, familyName);
insert into reservation (reservationno, guestno)
values (null, LAST_INSERT_ID());
END//
DELIMITER ;
Call it from your WinForms code like this:
dbcon.Open();
cmd = new MySqlCommand("CreateGuestAndReservation", dbcon);
cmd.CommandType = CommandType.StoredProcedure;
//cmd.Parameters.AddWithValue("?familyName", "foo");
cmd.Parameters.Add("?familyName", MySqlDbType.VarChar,255).Value = "foo";
cmd.ExecuteNonQuery();
The code below should work but I suspect you may have already tried it given that you are asking for help?
string sql = "INSERT INTO guest (guestno,familyname) VALUES(NULL,'Damn'); INSERT INTO reservation (reservationno, guestno) VALUES(NUll,LAST_INSERT_ID())";
If you need parameters, try this:
string sql = "INSERT INTO guest (guestno,familyname) VALUES(NULL,?familyName); INSERT INTO reservation (reservationno, guestno) VALUES(NUll,LAST_INSERT_ID())";
...
dbcmd.Parameters.Add("#familyName", MySqlDbType.VarChar, 80).Value = _familyName;
EDIT: You may need to run 2 insert commands. See here.
I would suggest having a way to get ids other than relying on automatic id generation like autoincrements of mysql and sql server, which are very limiting. If you use a HILO id generator you first obtain id, and then execute a couple of inserts in a single transaction no problem, since you know your parent id beforehand.
It will not solve your immediate problem, but it will help tremendeously in future with your application, especially if storing parent-children like data is going to occur often.
Try this, it will work:
private void button56_Click(object sender, EventArgs e) {
con.Open();
SqlCommand cmd = new SqlCommand("insert into stholidays values('" + dateTimePicker12.Text + "','" + dateTimePicker20.Text + "','" + dateTimePicker13.Text + "','" + mbk + "','" + dateTimePicker14.Text + "','" + dateTimePicker15.Text + "','" + lt + "','" + dateTimePicker16.Text + "','" + dateTimePicker17.Text + "','" + ebk + "','" + dateTimePicker18.Text + "','" + dateTimePicker19.Text + "','" + textBox105.Text + "','" + textBox106.Text + "','" + textBox107.Text + "','" + dd + "','" + textBox104.Text + "')", con);
SqlCommand cmd1 = new SqlCommand("insert into holidays values('" + dd + "','" + ms + "','" + day + "','" + textBox104.Text + "')", con);
cmd.ExecuteNonQuery();
cmd1.ExecuteNonQuery();
con.Close();
}

{"Incorrect syntax near 'C'."}.....Error Debug

SqlConnection conn = new SqlConnection("Server=ILLUMINATI;" +
"Database=DB;Integrated Security= true");
SqlCommand comm = new SqlCommand(
"Insert into FileUpload ('FilePath','TypeId','UploadedBy','UploadedDate')
values (" + savePath + "," + typeid + "," + NAME + "," + DateTime.Now+ ")", conn);
conn.Open();
comm.ExecuteNonQuery();
conn.Close();
It's giving an error saying:
{"Incorrect syntax near 'C'."}
Can anybody tell me the error please.
You have to put single '' quotes around the value strings not around the column names
try this
SqlCommand comm = new SqlCommand(
"Insert into FileUpload (FilePath,TypeId,UploadedBy,UploadedDate)
values ('" + savePath + "','" + typeid + "','" + NAME + "',"
assuming typeID is string, if not dont put '' around it
The reason it's giving the error is as Haris says - you're putting the single quotes in the wrong place.
However, it would be a very bad idea to "fix" this by just putting the quotes in different places. Instead, you should use a parameterized query:
SqlCommand comm = new SqlCommand
("Insert into FileUpload (FilePath, TypeId, UploadedBy, UploadedDate)" +
" values (#savePath, #typeid, #name, #now)", conn);
comm.Parameters.AddWithValue("#savePath", savePath);
comm.Parameters.AddWithValue("#typeid", typeid);
comm.Parameters.AddWithValue("#name", NAME);
comm.Parameters.AddWithValue("#now", DateTime.Now);
By expressing your data as data instead of as part of the "code" (the SQL) you avoid having to worry about conversions (e.g. date formats) and you avoid SQL injection attacks.
See the SqlCommand.Parameters documentation for more details (or search for "parameterized queries").
Enclose the columns, who has varchar and datetime type,in a single quote.
SqlCommand comm = new SqlCommand(
"Insert into FileUpload ('FilePath','TypeId','UploadedBy','UploadedDate')
values ('" + savePath + "'," + typeid + ",'" + NAME + "','" + DateTime.Now+ "')",
conn);

Categories