In mysql workbench, I can type
UPDATE contact_log
SET note = 'test1'
WHERE customer = 'customer'
and it will update the customer's note.
WHen i try this in asp.net, it has no effect.
Try
conn.Open()
cmd.Connection = conn
Catch ex As Exception
End Try
cmd.CommandText = "UPDATE contact_log " +
"SET note = '" & TextBox2.Text & "'" +
"WHERE customer = '" & Request.QueryString("ID") & "'"
reader = cmd.ExecuteReader()
conn.Close()
conn.Dispose()
Some facts are that the connection string is correct, I can use select and bring back data with no problem, and the request.querystring("ID") brings back the customer name.
Is there a better way to update a mysql table from asp.net, or a way that actually works?
Many problems in your code.
Do not use string concatenation to build sql commands, but
parameterized query
Do not catch exceptions and swallow them
Use the appropriate using statement to close and dispose the
connection
Of course an INSERT/UPDATE/DELETE statement requires ExecuteNonQuery
To summarize I would change your code to this
Dim cmdText = "UPDATE contact_log SET note = #note WHERE customer = #cust"
Using conn = new MySqlConnection(connString)
Using cmd = new MySqlCommand(cmdText, conn)
conn.Open()
cmd.Parameters.AddWithValue("#note",TextBox2.Text)
cmd.Parameters.AddWithValue("#cust",Request.QueryString("ID"))
Dim rowsAffected = cmd.ExecuteNonQuery()
End Using
End Using
Parameterized query are very important because you avoid Sql Injections and parsing problems with string containing quotes (You will get a syntax error if the TextBox2 contains a text with a single quote)
The Using Statement will ensure that youR connection is properly closed and disposed also in case of exceptions and you avoid dangerous memory leaks and get lower usage of system resources
The exception is better handled on a upper level of your code where you could show a message to your user or write in an error log. Catching an exception and doing nothing is very bad because you will never learn what is the reason of failure in your code.
You're using the wrong command... You're WRITING to the database, not reading from it - You need to change from using a reader to an execution command....
Try this:
cmd.CommandText = "UPDATE contact_log " +
"SET note = '" & TextBox2.Text & "'" +
"WHERE customer = '" & Request.QueryString("ID") & "'"
cmd.ExecuteNonQuery()
conn.Close()
conn.Dispose()
Related
I am trying to create unique policies with a ASP webservice and an Oracle 10.2g database.
I used to have a select query and an insert query to create policy numbers
But yesterday the webservice was called from 2 different threads and in the same exactly time and two same policy numbers where created.
So i changed the code to use a transation.
If the webservice is called from two different threads in the same time how will the transaction work?
Will the readcommited block the second thread or i will face the same problem again?
The select query will work or will there be a problem?
Public Function ExecutePolicyNumberTransaction(ByVal conet_key As String) As String
Dim policyno As String = ""
Dim sqlstring As String = ""
Dim conStr As String = ConfigurationManager.ConnectionStrings("con1").ConnectionString
Using connection As New OleDbConnection(conStr)
Dim transaction As OleDbTransaction
Try
connection.Open()
transaction = connection.BeginTransaction(IsolationLevel.ReadCommitted)
Dim insertcommand As New OleDbCommand()
insertcommand.Connection = connection
insertcommand.Transaction = transaction
sqlstring = " INSERT into POLICYNUMBERS ( " & _
" RECID, POLICYNO, REFERNCEKEY, ISUSED, ISUSEDDATE ) " & _
" (SELECT NVL(MAX(RECID),0)+1, concat('P0130',concat(to_char(SUBSTR('000000', 0, 6-length(to_char(NVL(MAX(RECID),0)+1)))),to_char(NVL(MAX(RECID),0)+1))), '" & ref_key & "', 1, sysdate " & _
" FROM POLICYNUMBERS )"
insertcommand.CommandText = sqlstring
insertcommand.ExecuteNonQuery()
transaction.Commit()
Dim selectcommand As New OleDbCommand()
selectcommand.Connection = connection
sqlstring = "SELECT POLICYNO FROM POLICYNUMBERS WHERE REFERNCEKEY = '" & ref_key & "'"
selectcommand.CommandText = sqlstring
policyno = selectcommand.ExecuteScalar()
Catch ex As Exception
Try
transaction.Rollback()
Catch
End Try
policyno = ""
End Try
End Using
Return policyno
End Function
In Oracle, readers don't block writers and writers don't block readers. So neither session will block the other.
In a multi-user environment, however, you cannot generate primary keys using MAX(key)+1 unless you specifically introduce some form of serialization. Unless you want to build slow, unreliable systems, you don't want to introduce serialization. Instead, you really, really, really want to be using a sequence to generate your keys. Sequences are specifically designed to give primary keys to multiple concurrent sessions with a minimal overhead.
CREATE SEQUENCE policy_recid_seq
START WITH 1
INCREMENT BY 1
CACHE 100;
INSERT INTO policynumbers
SELECT policy_recid_seq.nextval, ...
I have a code which checks the validity of user and then, if a user is valid it inserts certain values in the database.
My problem is when After I query my database to check if a user is valid and after that i try to pass the additional value to its account the flow stops when I invoke ExecuteReader() for the second time.
There is no error, or anything like that. I tried to substitute ExecuteReader() with ExecuteNoneQuery but still it's not working. I tried all the query in mysql command prompt they are working perfectly. I really can't understand what am I doing wrong there. Can anyone help me please?
Here is the code:
Try
myconn.Open()
Dim stquery As String = "SELECT * from accountstbl WHERE SE_ID = " & Id.Text
Dim smd = New MySqlCommand(stquery, myconn)
Dim myreader = smd.ExecuteReader()
If Not myreader.HasRows Then
errorUser.Visible = True
Else
myreader.Read()
Dim name As String = myreader.Item("user_name").ToString()
Dim stquery2 = "INSERT into backup VALUES (" & name & ", '" & Info & "')"
Dim smd2 = New MySqlCommand(stquery2, myconn)
Dim Myreader2 As MySqlDataReader
'smd.ExecuteNonQuery()'
'THE CODE STOPS HERE'
Myreader2 = smd2.ExecuteReader()
'Myreader2.Read()'
MsgBox("The BACKUP INFORMATION HAS BEEN SAVED")
End If
myconn.Close()
Catch ex As Exception
Dim ErrorMessage As String = "alert('" & ex.Message.ToString() & "');"
Page.ClientScript.RegisterStartupScript(Me.GetType(), "ErrorAlert", ErrorMessage, True)
myconn.Close()
End Try
Because your second query is an update, not a select, you need to execute it using the ExecuteNonQuery method. Your commented-out code shows an attempt to call ExecuteNonQuery but on the wrong command object (smd when it should be smd2). Try something like this instead:
myreader.Read()
Dim name As String = myreader.Item("user_name").ToString()
Dim stquery2 = "INSERT into backup VALUES (" & name & ", '" & Info & "')"
Dim smd2 = New MySqlCommand(stquery2, myconn)
smd2.ExecuteNonQuery()
The ExecuteNonQuery method returns the number of rows updated as an int value, so you can capture it if it's valuable to you. In your case it's probably not, but here's how you'd check anyway:
int rowsAdded = smd2.ExecuteNonQuery();
if (rowsAdded == 1) {
// expected this
} else {
// didn't expect this
}
Finally, concatenating strings to build SQL commands can leave you vulnerable to SQL Injection attacks. Please take a look at using parameterized queries. There's a decent example here.
If you want to execute nested Reader, you have to create another connection. You need somethig like
smd2 = New MySqlCommand(stquery2, myconn2)' myconn2 is another connection
OR
Set "MultipleActiveResultSets=True in your connection string.
Also, use ExecuteNonQuery() for Inserting
Dim name As String = myreader("user_name").ToString()
Dim stquery2 = "INSERT into backup VALUES ('" & name & "', '" & Info & "')"
Dim smd2 = New MySqlCommand(stquery2, myconn)
smd.ExecuteNonQuery()
Please use Parameterized query to avoid SQL Injection
The logic is that you need to close your first reader (myreader) before executing another reader (MyReader2) on the same connection.
I'm trying to update a record from an Ms-Access table with VB.NET and ASP.NET. I'm getting 2 errors:
On the web page that's opened I'm getting Thread was being aborted
Web Developer 2010 gives me an error says there's an error in the
UPDATE statement
This is the code so far:
Imports System.Data.OleDb
Partial Class ChangePassword
Inherits System.Web.UI.Page
Protected Sub btnChange_Click(sender As Object, e As System.EventArgs) Handles btnChange.Click
Dim tUserID As String = Session("UserID")
Dim conn As New OleDbConnection("Provider=Microsoft.Jet.OLEDB.4.0;Data Source=C:\Users\Brian\Documents\Visual Studio 2010\WebSites\WebSite3\db.mdb;")
conn.Open()
Dim cmd As OleDbCommand = New OleDbCommand("SELECT * FROM [User] where UserID=?", conn)
Dim cmd2 = New OleDbCommand("UPDATE USER SET [Password] = '" + txtConfPass.Text + "' where UserID = '" + tUserID + "'", conn)
cmd.Parameters.AddWithValue("#UserID", tUserID)
Dim read As OleDbDataReader = cmd.ExecuteReader()
Dim read2 As OleDbDataReader = cmd2.ExecuteReader()
lblUser.Text = tUserID.ToString
lblUser.Visible = True
If read.HasRows Then
While read.Read()
If txtOldPass.Text = read.Item("Password").ToString Then
cmd2.ExecuteNonQuery()
lblPass.Visible = True
End If
End While
Else
lblPass.Text = "Invalid Password."
lblPass.Visible = True
End If
conn.Close()
lblPass.Text = tUserID.ToString
lblPass.Visible = True
Any help would be appreciated.
Thanks !
First, your cmd2 fails because USER is a reserved word. Enclose in
square brackets as you already do in the first OleDbCommand.
Second, to execute a statement like UPDATE, INSERT, DELETE you call
cmd2.ExecuteNonQuery not ExecuteReader. Don't really needed that call
after the first for cmd.
Third, in the first OleDbCommand (cmd) you use a parameter for
UserID, why in the second one you revert to string concatenation for
user and password? This opens the door to any kind of Sql Injection
Attack.
Fourth, the Using statement assure that every Disposable object
used in your code will be CLOSED thus freeing the memory used by
this commands ALSO IN CASE OF EXCEPTIONS. An example of Using
statement here
(1)
Dim read2 As OleDbDataReader = cmd2.ExecuteReader()
and then
(2)
cmd2.ExecuteNonQuery()
Remove (1) - ExecuteNonQuery should do the update.
USER is a keyword in Access, add brackets the same way you have added in the Select statement. Next time, you are faced with a similar problem, print out the statement as Access would see it and try executing it on the database directly - that will point out the errors accurately.
Please use place holders for the update statement similar to the select statement.
I have a web application and on page is an update page to update some profile information. Below is the code I am using to update the table. But I think it is wrong. Does anything stick out? The connection string works cause it is used to read the database to get the profile information, I just removed it due to it containing password/login info for the db.
player is the class of properties that contains player information and ds is the dataset, but I would like to update the database itself online...
Dim connectionString As String = ""
Dim GigsterDBConnection As New System.Data.SqlClient.SqlConnection(connectionString)
GigsterDBConnection.Open()
Dim updatetoursql As String = "UPDATE PLAYERS SET FIRSTNAME = '" & player.FIRSTNAME & "', LASTNAME = '" & player.LASTNAME & "', ADDRESS = '" & player.ADDRESS & "', CITY = '" & player.CITY & "', ZIP = '" & player.ZIP & "', PHONE = '" & player.PHONE & "', EMAIL = '" & player.EMAIL & "', REFFEREDBY = '" & player.REFEREDBY & "' "
updatetoursql = updatetoursql & "PLAYERID = '" & player.PLAYERID & "';"
Dim cmd As New System.Data.SqlClient.SqlCommand(updatetoursql, GigsterDBConnection)
Dim sqlAdapter As New System.Data.SqlClient.SqlDataAdapter(cmd)
sqlAdapter.Update(ds, "PLAYERS")
I think the issue is something the 3 last lines of the code. am I doing it right or is their a better way?
Thanks
Well, apart from the glaring SQL injection issues waiting to bite you ..... (hint: use parametrized queries instead of concatenating together your SQL statement!!)
Dim cmd As New SqlCommand(updatetoursql, GigsterDBConnection)
Dim sqlAdapter As New SqlDataAdapter(cmd)
The problem here is: if you call the SqlDataAdapter constructor this way, what you're passing in is the select command (of the data adapter) - not the update command!
You need to do it this way:
Dim cmd As New SqlCommand(updatetoursql, GigsterDBConnection)
Dim sqlAdapter As New SqlDataAdapter()
sqlAdapter.UpdateCommand = cmd;
Now you've associated your UPDATE statement with the SqlDataAdapter.UpdateCommand and now it should work.
About the SQL injection: I'd strongly recommend using parametrized queries all the time - at least in production code. So instead of concatenating together your query, use this:
Dim updatetoursql As String =
"UPDATE PLAYERS SET FIRSTNAME = #FirstName, LASTNAME = #LastName, " &
"ADDRESS = #Address, CITY = #City, ZIP = #Zip, PHONE = #Phone " &
"EMAIL = #EMail, REFFEREDBY = #ReferredBy, PLAYERID = #PlayerID"
and then before you execute the command or the SqlDataAdapter.Update statement, set those parameters to the values you have. This is much safer and gives you less headaches and possibly even speed improvements (if that single Update query is only cached once in SQL Server memory).
Also, why go the long and complicated way of a SqlDataAdapter at all??
After you've created the SqlCommand and set all the parameters, just call cmd.ExecuteNonQuery(); and you're done!
Dim cmd As New SqlCommand(updatetoursql, GigsterDBConnection)
// set up the parameters here.....
cmd.Parameters.AddWithvalue("#FirstName", FirstName);
... etc.
// just call ExecuteNonQuery - and you're done!
cmd.ExecuteNonQuery();
The big thing that jumps up at me is how open to SQL Injection attacks this code is.
You should not build a SQL string in this manner, but use parameterized queries.
Other then that, you are constructing your adapter incorrectly, as the constructor will take the select command, not the update command. Create the command with the parameterless constructor then assign the command you have created to the UpdateCommand property.
I have this code:
Dim pathString As String = HttpContext.Current.Request.MapPath("Banking.mdb")
Dim odbconBanking As New OleDbConnection _
("Provider=Microsoft.Jet.OLEDB.4.0;" & _
"Data Source=" + pathString)
Dim sql As String
sql = "UPDATE tblAccounts balance = " & CDbl(balance + value) & " WHERE(accountID = " & accountID & ")"
odbconBanking.Open()
Dim cmd As New OleDbCommand(sql, odbconBanking)
cmd.ExecuteNonQuery()
However, an exception is thrown, when I run it:
Syntax error in UPDATE statement.
I tried to run a similar statement in Access and it works fine.
I think the missing is SET.
Try: UPDATE table SET field = newvalue WHERE criteria;
Just modify:
sql = "UPDATE tblAccounts SET balance = " & CDbl(balance + value) & " WHERE(accountID = " & accountID & ")"
http://office.microsoft.com/en-us/access/HA100765271033.aspx
The SQL Statement definitely is missing the SET keyword. Also, I suggest you to brush up on parameterized query:
Dim sql As String = "UPDATE tblAccounts " & _
"SET balance = ? " & _
"WHERE(accountID = ?)"
Dim cmd As New OleDbCommand(sql, odbconBanking)
cmd.Parameters.Add("Balance", CDbl(balance + value))
cmd.Parameters.Add("AccountId", accountID
cmd.ExecuteNonQuery()
This way, not only is the SQL Statment is clearer, it help prevents possible SQL injection attacks.
You are missing SET as part of UPDATE.
It should be UPDATE tablename SET fieldname = ... WHERE [criteria].
On a side note, you are using classic asp style code inside asp.net. I will suggest reading some docs on ASP.net and how to design applications in a layered manner.
A good start is here: Enterprise Library's Data Access Application Block
Link: https://web.archive.org/web/20210612110113/https://aspnet.4guysfromrolla.com/articles/030905-1.aspx