I am trying to update a particular column of a SQL Server table using my aspx page on button click event. My code is:
if (AutoMan.Text == "Auto Mode")
{
var x = "1";
var y = DateTime.Now.ToString();
var z = "1";
using (SqlConnection con = new SqlConnection(#"Data Source=localhost.\SQLEXPRESS;Initial Catalog=MCAS;Integrated Security=SSPI;"))
{
con.Open();
try
{
using (SqlCommand cmd = new SqlCommand("UPDATE AutoManLog SET AutoMan = #data, Time = #data1", con))
{
cmd.Parameters.AddWithValue("#data1", y);
cmd.Parameters.AddWithValue("#data", x);
cmd.ExecuteNonQuery();
}
}
catch (Exception Ex)
{
Response.Write("Unable To Save Data. Error - " + Ex.Message);
}
con.Close();
}
Data in the database is not updating. I Can't see any error messages.
in this query:
"UPDATE AutoManLog SET AutoMan = #data, Time = #data1"
Time is a preserved name for sql server; so use it as [Time] will be solve the problem,
if there isn't another problem exist.
I copy-pasted your code and it works just as is; your parameters are correct, and your statement is correct.
Your possible issues are:
AutoMan.Text does not equal "Auto Man" -- make sure they are equal
Any error occurring (database connection, table doesn't exist, etc.), but something is obstructing your Response.Write output, not making you able to see the output -- take out the try-catch, and let the debugger catch errors so you can trace it better
Related
As a beginner to c#, and I actaully spent a lot of time researching this:
I cannot add some data into the database, I can extract data from it, but cannot add anything into the database. I use sql server as my database.
try {
fname = fname_tb.Text;// first name
sname = sname_tb.Text; // second name
q = "insert into beforebath1(firstname,secondname) values(#fname,#sname)";
conn_string = Properties.Settings.Default.beforebath_connection_string;
SqlConnection co = new SqlConnection(conn_string);
SqlCommand cmd;
co.Open();
cmd = new SqlCommand(q, co);
cmd.Connection = co;
cmd.Parameters.AddWithValue("#fname", fname_tb.Text);
cmd.Parameters.AddWithValue("#sname", sname_tb.Text);
cmd.ExecuteNonQuery();
co.Close();
}
catch(Exception err) {
MessageBox.Show(err.toString());
}
my sql connection string is this:
Data Source=(LocalDB)\v11.0;AttachDbFilename=|DataDirectory|\beforebath_db.mdf;Integrated Security=True;Connect Timeout=30
It is automatically generated when I created the database. Please help me insert the text in the two textboxes (fname_tb.Text and sname_tb.Text) into the table called beforebath1 of the database called beforebath_db.mdf.
Is it something to do with my data directory?
I see a couple of mistakes in your code.
First, why catch an exception that will only be shown in a message?
It is often best to let the exception bubble up to have the stack trace in debug. This is not the same if this is production code, which I doubt.
Second, make sure to dispose your objects adequately.
The Using Statement is the most prefered way to work with disposeable items such as a database connection and a command.
using (var cnx = new SqlConnection(connectionString)) {
cnx.Open();
var sql = #"insert into beforebath1 (first_name, second_name)
values (#fname, #lname)";
using (var cmd = new SqlCommand(sql, cnx)) {
cmd.Parameters.AddWithValue("#fname", fname_tb.Text);
cmd.Parameters.AddWithValue("#lname", lname_tb.Text);
try {
int rowsAffected = cmd.ExecuteNonQuery();
if (0 < rowsAffected) MessageBox.Show("Success!");
else MessageBox.Show("Failed!");
} catch (SqlException ex) {
// It is almost prefered to let the exception be thrown freely
// so that you may have its full stack trace and have more
// details on your error.
MessageBox.Show(ex.Message);
} finally {
if (cnx.State == ConnectionState.Open) cnx.Close();
}
}
}
This way, wrapping your disposable objects within using blocks, you make sure that everything is getting to get disposed automatically when exiting the code block.
As for your "it doesn't work" problem, I guess the problem be either at the connection string level, or at your table_name level.
You wish to insert into beforebath1, and your insert statement states table_name. Make sure you put the right table name where it belongs so that it may work properly.
Can you change you connection string to this:
Server=(LocalDB)\v11.0;Database=beforebath_db;Trusted_Connection=True;
This means the your app and other programs using the Db will all share the same instance.
Also, as mentioned by #Will, you should wrap your SQLConnection in a using statement for garbage collection.
For better implementations you can use stored_procedures like bellow:
Step1: Declare Stored Procedure for your Query:
CREATE PROCEDURE [dbo].[ADD_TO_BEFORE_PATH_SP]
/*Type of this variables should be their column types*/
#fname varchar(MAX),
#lname varchar(MAX)
AS
BEGIN
INSERT INTO [dbo].[beforebath1] (fname, lname)
VALUES (#fname,#lname)
END
Step2: Using Stored Procedure where you need:
SqlConnection con = new SqlConnection(connectionString);
SqlCommand com = new SqlCommand("ADD_TO_BEFORE_PATH_SP", con);
com.Parameters.AddWithValue("#fname", fname_tb.Text);
com.Parameters.AddWithValue("#lname", lname_tb.Text);
com.CommandType = CommandType.StoredProcedure;
try
{
con.Open();
com.ExecuteNonQuery();
}
catch (Exception)
{
throw;
}
finally
{
if (con.State == ConnectionState.Open)
con.Close();
}
I'm using Visual Studio 2010 to create a Win Form in c#. It has a handful of Comboboxes, and textboxes that the user can fill out and then submit to an Access DB. My issue comes in when I try to update existing entries. I load an existing entry, make my changes and click update. I do not get any system errors, my connection to the DB is successful, but no changes are actually made to the data. Am I completely missing something? Thanks in advance for any help or insight.
Here is the code for the update button:
private void updateButton_Click_1(object sender, EventArgs e)
{
{
OleDbConnection conn = new OleDbConnection();
conn.ConnectionString = #"Provider=Microsoft.Jet.OLEDB.4.0;Data Source=|DataDirectory|\servicereq1.mdb";
OleDbCommand cmd = new OleDbCommand("UPDATE servicereq SET DateLogged = #datelogged, LoggedBy = #loggedby, Function = #function, [Other Impacts] = #summary, Account = #earningsaccount, [From] = #from, [To] = #to, Description = #description, Fixer = #fixer, [Time Estimate] = #timeestimate, [Actual Start] = #actualstart, [Actual Finish] = #actualfinish, [Actual Time] = #actualtime, [Programs/Forms] = #programsforms, Comments = #comments, [Retest Date] = #requestdate, Tester = #tester, Status = #status, [Problem In Environment] = #problemfoundin, [Code In Environment] = #codein WHERE (ServiceRequestNumber = #servreq)");
cmd.Connection = conn;
conn.Open();
if (conn.State == ConnectionState.Open)
{
cmd.Parameters.AddWithValue("#servreq", serviceRequestNumberTextBox.Text);
cmd.Parameters.AddWithValue("#datelogged", dateLoggedTextBox.Text);
cmd.Parameters.AddWithValue("#loggedby", loggedByComboBox.Text);
cmd.Parameters.AddWithValue("#problemfoundin", problem_In_EnvironmentComboBox.Text);
cmd.Parameters.AddWithValue("#function", functionTextBox.Text);
cmd.Parameters.AddWithValue("#summary", other_ImpactsTextBox.Text);
cmd.Parameters.AddWithValue("#earningsaccount", accountTextBox.Text);
cmd.Parameters.AddWithValue("#from", fromTextBox.Text);
cmd.Parameters.AddWithValue("#to", toTextBox.Text);
cmd.Parameters.AddWithValue("#status", statusComboBox.Text);
cmd.Parameters.AddWithValue("#description", descriptionTextBox.Text);
cmd.Parameters.AddWithValue("#fixer", fixerComboBox.Text);
cmd.Parameters.AddWithValue("#codein", code_In_EnvironmentComboBox.Text);
cmd.Parameters.AddWithValue("#programsforms", programs_FormsTextBox.Text);
cmd.Parameters.AddWithValue("#timeestimate", time_EstimateTextBox.Text);
cmd.Parameters.AddWithValue("#actualstart", actual_StartTextBox.Text);
cmd.Parameters.AddWithValue("#actualfinish", actual_FinishTextBox.Text);
cmd.Parameters.AddWithValue("#actualtime", actual_TimeTextBox.Text);
cmd.Parameters.AddWithValue("#requestdate", retest_DateTextBox.Text);
cmd.Parameters.AddWithValue("#tester", testerComboBox.Text);
cmd.Parameters.AddWithValue("#comments", commentsTextBox.Text);
try
{
cmd.ExecuteNonQuery();
MessageBox.Show("Form Updated Successfully");
conn.Close();
}
catch (OleDbException ex)
{
MessageBox.Show(ex.Message);
conn.Close();
}
}
else
{
MessageBox.Show("Connection Failed");
}
}
}
You shouldn't put your database parameters within quotes - they are evaluated as plain text instead of parameters if you do. There is no row where ServiceRequestNumber equals the literal string '#servreq', so nothing is updated.
Also, DataCommands don't pull in local variables as parameters - they must be explicitly added to the DataCommand object (cmd in this case). The reason you aren't getting any errors when you remove your parameter-adding code is because, as stated above, the query doesn't expect any parameters.
Also, the way parameters are being added in the code you removed is strange to say the least. This is much more normal, and significantly easier to read:
cmd.Paramaters.AddWithValue("#paramName", paramData);
//or
cmd.Parameters.Add(new OleDbParameter("#paramName", paramData));
After spending a little more time editing and moving code around, I stumbled on the fact that your parameters must be in the same order in the query as they are when you bind values to them. After making syntactical changes suggested by JoFlash Studios and putting my parameters in the correct order, I was able to make edits to existing data in my form.
Earlier I posted this code but it was much more messy, parts were commented out, and I was using concatenation to INSERT to the database. I was told to clean it up, challenged to use parameters, and ask more concise questions. With that being said, the connection to the database was given to me with mostly pseudo-code with some direct commands.
1) Is my Try-Catch set up correctly?
2) "server = LOCALHOST" is underlined in red, it says it can't convert 'string' to System.Data.SqlClient.SqlConnection'
3) "Database" and "Lab1" are underlined saying it doesn't exist in current context? What does this mean?
4) "Trusted_connection" and "yes" have the same error message as #3.
5) I'm not sure what to put after "cmd.Connection = " which is why it's commented out and has a question mark after it.
6) Is my varname1.Close(); in the right spot? I feel like it makes sense for it to actually go between the last 2 closing brackets?
7) In the Catch "SqlException" is underlined and the error says "The type or namespace SqlException could not be found". I found a try-catch from another user on stackoverflow that asked the question and someone responded with the catch set up like that so I copied it.
8) I'm trying to figure out parameters, Is mine set up correctly? All I have is 1 textbox in which the user inputs data and it enters into an array. "Name" is the name of the attribute of the student in the database, and I just made up #Name as a variable? I found a parameter example from another user also on stackoverflow and kind of made match mine.
public static int counter = 0;
protected void btnDisplay_Click(object sender, EventArgs e)
{
try
{
System.Data.SqlClient.SqlConnection varname1 = new System.Data.SqlClient.SqlConnection();
varname1 = "server = LOCALHOST";
Database = Lab1;
Trusted_connection = yes;
varname1.Open();
System.Data.SqlClient.SqlCommand cmd = new System.Data.SqlClient.SqlCommand();
// cmd.Connection = (?)
cmd.CommandText = "Delete From Student";
cmd.ExecuteNonQuery();
for(int i=0; counter >= i; i++)
{
cmd.CommandText = "INSERT INTO Lines (Name) " + "VALUES (#Name)";
cmd.Parameters.AddWithValue("#Name", studentList[i]);
counter++;
}
varname1.Close();
}
catch (SqlException ex)
{
lbl5.Text = "Connection could not be established";
}
}
You need to find a good resource (or a few) and learn how to make proper database calls. Here's one. Here's another, on creating connection strings.
I haven't tested the following, but something like this should work.
using (var conn = new System.Data.SqlClient.SqlConnection("Server=LOCALHOSTDatabase=Lab1;Trusted_Connection=True;"))
{
conn.Open();
using (var cmd = new SqlCommand("Delete From Student", conn))
{
cmd.ExecuteNonQuery();
}
using (var cmd = new SqlCommand("INSERT INTO Lines (Name) VALUES (#Name)", conn))
{
for (int i = 0; counter >= i; i++)
{
cmd.Parameters.Clear();
cmd.Parameters.AddWithValue("#Name", studentList[i]);
cmd.ExecuteNonQuery();
}
counter++;
}
}
As for some of your other questions...
#1 - Your try/catch is setup okay.
#6 - Don't bother calling Close() - use a using block
#7 - The exception name looks okay. Do you have using System.Data.SqlClient; at the top of your form? You may be getting an error here because of other lines of code with errors... hard to say.
#8 - That looks fine.
You should have a finally block with your try-catch
Your SQLConnection should be created with the connection string as a parameter. You can't set it equal to a String, it's a SQLConnection.
I don't know where Database and Lab1 are declared but it's obviously not within the scope of your function.
See 3. And yes has no meaning.
cmd.Connection = varName1
You should close your connection in a finally block to ensure it is closed even if an exception is thrown
Have you imported System.Data.SQLClient?
Adding parameters with values will replace #Name in your SQL string with the value you supplied
I have a code written that automatically adds and reads information from my SQL Server 2012 Express table, Logins. But it wont work, here is the code:
private void Form1_Load(object sender, EventArgs e)
{
SqlConnection myConnection = new SqlConnection("user id=myComputer;" + "server=MYCOMPUTER-PC\\SQLEXPRESS;" +
"Trusted_Connection=yes;" + "database=loginTest; " + "connection timeout=5");
try
{
myConnection.Open();
}
catch (Exception ex)
{
MessageBox.Show(ex.ToString());
}
SqlCommand myCommand = new SqlCommand("INSERT INTO dbo.Logins Values ('John','Password','Admin')", myConnection);
try
{
SqlDataReader myReader = null;
SqlCommand myCommand1 = new SqlCommand("select * from Logins",
myConnection);
myReader = myCommand1.ExecuteReader();
while (myReader.Read())
{
MessageBox.Show(myReader["Column1"].ToString());
MessageBox.Show(myReader["Column2"].ToString());
}
}
catch (Exception ex1)
{
MessageBox.Show(ex1.ToString());
}
}
I have debugged the program and it all seems to go through fine, it skips over :
{
MessageBox.Show(myReader["Column1"].ToString());
MessageBox.Show(myReader["Column2"].ToString());
}
for some reason, and it doesnt write the values i told it to.
Can anyone tell me why? Im a beginner at SQL, so go easy please :)
PS It doesnt fire out any error codes or exceptions
You Logins table doesn't have any records, if you mean you want to try inserting some record first to test, it's this line causing your problem:
SqlCommand myCommand = new SqlCommand("INSERT INTO dbo.Logins Values ('John','Password','Admin')", myConnection);
myCommand.ExecuteNonQuery();//Do this to insert something into your Logins first.
it skips over [...]
Presumably that's because there's no data to read, so myReader.Read() just returns false.
it doesnt write the values i told it to.
You don't actually tell it to write anything. You create a SqlCommand to insert data, but you never execute it. You need to use myCommand.ExecuteNonQuery. You should also use using statements for the commands, the connection and the reader, to make sure they get closed properly.
public TransImport()
{
ConnString = ConfigurationManager.ConnectionStrings["Connection"].ConnectionString;
SqlConnection conn_new;
SqlCommand command_serial_new;
SqlConnection conn;
SqlCommand command_serial;
SqlTransaction InsertUpdateSerialNumbers;
conn = new SqlConnection(ConnString);
command_serial = conn.CreateCommand();
conn_new = new SqlConnection(ConnString);
command_serial_new = conn_new.CreateCommand();
command_serial_new.CommandText = "SELECT 1 FROM YSL00 WHERE SERLNMBR = #slnr";
var p = new SqlParameter("#slnr", SqlDbType.NVarChar, 50);
command_serial_new.Parameters.Add(p);
//Here you will start reading flat file to get serialnumber.
InsertUpdateSerialNumbers = conn.BeginTransaction();
while (!headerFileReader.EndOfStream)
{
headerRow = headerFileReader.ReadLine();
if (CheckSerialNumber(headerFields[0].Trim()))
DisplayMessage("Good serialnumber"); //this function is not copied here.
}
InsertUpdateSerialNumbers.Commit();
}
private Boolean CheckSerialNumber(string SerialNumber)
{
command_serial_new.Parameters["#slnr"].Value = SerialNumber;
try
{
var itExists = Convert.ToInt32(command_serial_new.ExecuteScalar()) > 0;
if (!itExists)
{
command_serial.Transaction = InsertUpdateSerialNumbers;
command_serial.CommandText = "INSERT INTO YSL00([Manifest_Number],[PONUMBER],[ITEMNMBR],[SERLNMBR]"
+ "VALUES ('" + Manifest + "','" + PONr + "','" + itemNumber + "','" + serialNr + "')";
var insertStatus = command_serial.ExecuteNonQuery();
return true;
}
}
catch (Exception ex)
{
LogException(ex, "Error in CheckSerialNumber =>"+ command_serial_new.CommandText.ToString());
}
return false;
}
I get error "Timeout expired. The timeout period elapsed prior to completion of the operation or server is not responding".
The CheckSerialNumber function also does an insert to YSL00 (the same table where I had executescalar. See code above).
As I mentioned earlier there are 1000s of line in a flat file that I read and update YSL000 table.
Note that I have two separate sqlcommands and also two separate connections to handle this. Reason is with sqltransaction it doesn't let me to query on the same table. I think timeout may be happening because of this?
Thanks for reading. Please suggest
Update 1: Since I have not pasted entire code, I want to mention that dispose is done using below code in the program.
if (conn != null)
{
conn.Close();
conn.Dispose();
}
if (conn_new != null)
{
conn_new.Close();
conn_new.Dispose();
}
you can increase the time out of your SqlConnection object.
you can do this with your ConnString:
string connStr = "Data Source=(local);Initial Catalog=AdventureWorks;Integrated
Security=SSPI;Connection Timeout=300";
I think default isolation level - read commited - is preventing your 'CheckSerialNumber' method from being effective. Command_serial_new will not take into consideration rows inserted in your loop - this might lead to some troubles. To be honest I would also look for some deadlock. Perhaps command_serial_new is actually completely blocked by the other transaction.
To start off:
Set command_serial_new query as:
SELECT 1 FROM YSL00 WITH (NOLOCK) WHERE SERLNMBR = #slnr
Think about using lower isolation level to query inserted rows as well (set it to read uncommited).
Close your connections and transactions.
Use just one SqlConnection - you don't need two of them.
Many of the objects you are using implement IDisposable, and you should be wrapping them with using statements. Without these using statements, .NET won't necessarily get rid of your objects until an undetermined time when the garbage collector runs, and could block subsequent queries if it's still holding a transaction open somewhere.
So for example, you'll need to wrap your connections with using statements:
using (conn_new = new SqlConnection(ConnString)) {
...
If I am not mistaken you need to merge the file content with the table content.
For this purpose I would recommend you
Copy the file content in to a temporary table (see temporary tables and BulkInsert)
Use command MERGE (http://msdn.microsoft.com/en-us/library/bb510625.aspx) to merge the temporary table content with the original table