我是VB的新手。自从我开始学习VB以来已经有几周了。我的问题是我很难将数据添加到VB中的数据库(我正在使用MS Access)。到目前为止,我得到了这段代码,但运行不顺利:
Imports System.Data.OleDb
Public Class CraeteAccount
Dim connString As String
Dim myConnection As OleDbConnection = New OleDbConnection
Dim cmd As New OleDbCommand
Dim dr As OleDbDataReader
Public Sub btnCreate_Click_1(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles btnCreate.Click
connString = "Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" & IO.Path.Combine(My.Application.Info.DirectoryPath, "LogIn1.accdb")
Dim cmd As New OleDbCommand
Dim cnn As OleDbConnection = New OleDbConnection(connString)
Dim str As String
Dim UserName As String
Dim Password As String
If txtPassword.Text = txtRetype.Text Then
cnn.Open()
Try
UserName = txtUserName.Text
Password = txtPassword.Text
str = "UPDATE Users SET UserName= '" & UserName & "', Password= '" & Password
cmd = New OleDbCommand(str, myConnection)
cmd.Parameters.AddWithValue("@UserName", UserName)
cmd.Parameters.AddWithValue("@Password", Password)
cmd.ExecuteNonQuery()
MsgBox("New User has been Created!")
cnn.Close()
Me.Hide()
Catch ex As Exception
MsgBox("Error Occured!")
cnn.Close()
End Try
Me.Close()
Else
MsgBox("Check your Password!")
cnn.Close()
txtPassword.Focus()
End If
End Sub
当代码运行时它不会添加数据并快速捕获以显示消息框,其中显示“Error Occured”。那么有人可以帮帮我吗?
答案 0 :(得分:2)
快速浏览一下,SQL查询会以多种方式破解:
str = "UPDATE Users SET UserName= '" & UserName & "', Password= '" & Password
首先要注意的是,您不会在密码后关闭引号。然而,即使这不是你真正想做的事情。你想要做的是:
str = "UPDATE Users SET UserName=@UserName, Password=@Password"
这将创建查询参数,接下来的两行将使用值填充:
cmd.Parameters.AddWithValue("@UserName", UserName)
cmd.Parameters.AddWithValue("@Password", Password)
将用户值直接放入查询中称为SQL注入漏洞。它允许用户在您的数据库上执行任意代码,这显然是一件坏事。所以你肯定会想要坚持使用这些参数。
这里的第二个问题是这个查询将更新表中的每个记录。所以它基本上会用这一条记录的多个副本覆盖所有 Users
条记录。
如果此确实应该是UPDATE
语句,当您想要向其添加WHERE
子句时,该子句将标识特定的要更新的记录。
然而,我怀疑基于上下文这应该是INSERT
语句,因为它创建新记录:< / p>
str = "INSERT INTO Users (UserName, Password) VALUES (@UserName, @Password)"
此外,这很重要,您将用户密码存储在纯文本中。这对您的用户 严重不负责任 。您应该使用单向哈希模糊用户密码,以便永远以原始形式检索它们。您甚至不是系统管理员。
(对于初学者来说,这里使用的语言和重点可能有点苛刻。特别是如果你正在从事一个没有实际用户的纯粹学术项目。但它非常重要。而且&#&# 39;没有时间像现在这样了解它。)
此处的另一个问题是您认为查询成功:
cmd.ExecuteNonQuery()
MsgBox("New User has been Created!")
至少应该检查返回值以确保记录实际受到影响:
Dim rowsAffected As Int32 = cmd.ExecuteNonQuery()
If rowsAffected > 0 Then
MsgBox("New User has been Created!")
Else
'no record was inserted, handle error condition
End If
您面临的另一个问题,与您的问题没有直接关系,但 让您调试问题变得更加困难,是您&#39 ;重新忽略错误信息:
Catch ex As Exception
MsgBox("Error Occured!")
cnn.Close()
在此代码块中,ex
变量包含.NET Framework可以为您提供有关发生的错误的所有信息。您基本上做的是用一条不包含任何信息的自定义错误消息替换所有诊断信息(错误消息,堆栈跟踪等)。
最好不要这样做。
请注意,鉴于这些问题,代码可能存在其他问题。但这至少应该让你有所收获。
答案 1 :(得分:0)
您同时尝试将更新语句与用户输入(错误)连接并使用参数化值(好)。尝试
str = "UPDATE Users SET UserName=@UserName, Password=@Password"
cmd = New OleDbCommand(str, myConnection)
cmd.Parameters.AddWithValue("@UserName", UserName)
cmd.Parameters.AddWithValue("@Password", Password)
但是这仍然无法正常工作,因为此更新语句将使用这些值更新数据库中的所有记录。您是在尝试更新现有记录还是创建新记录?如果您要更新现有的,则需要WHERE子句;如果您正在尝试创建新的,则需要使用INSERT。