Невозможно вставить, даже если запись все еще не существует в базе данных - PullRequest
0 голосов
/ 12 января 2012

Я хочу вставить записи в базу данных, но перед вставкой он должен сначала проверить базу данных, существует ли уже добавляемое значение. Теперь моя проблема в том, что я не могу вставить в базу данных, хотя значение все еще не существует.

Вот мой код:

Dim check As New SqlCommand
    Dim sqlcheck As String = "SELECT SerialNumber FROM EquipmentDetail WHERE SerialNumber = '" & TextBox1.Text & "'"


    connection.Open()
    check.Connection = connection
    check.CommandText = sqlcheck

    Dim read As SqlDataReader = check.ExecuteReader()

    If read.HasRows Then

        While read.Read()

            If read("SerialNumber").ToString() = TextBox1.Text Then

                MessageBox.Show(read("SerialNumber").ToString() & " was already added")

            Else

                cmd.Connection = connection
                cmd.CommandText = "INSERT INTO EquipmentDetail (SerialNumber, BoxNumber, FATTNumber, FaultTicketNumber, Description, ProductCode)" &
                "VALUES('" & TextBox1.Text & "',  '" & TextBox2.Text & "',  '" & TextBox3.Text & "',  '" & TextBox4.Text & "', '" & TextBox6.Text & "',  '" & ComboBox1.Text & "')"
                cmd.ExecuteNonQuery()

                MessageBox.Show("Equipment successfully added.", "Equipment", MessageBoxButtons.OK)
                TextBox1.Text = ""
                TextBox2.Text = ""
                TextBox3.Text = ""
                TextBox4.Text = ""
                TextBox6.Text = ""
                TextBox1.Focus()
                connection.Close()

            End If
        End While
    End If
    read.Close()

Ответы [ 3 ]

2 голосов
/ 12 января 2012

Существует ряд проблем с вашим кодом.

Во-первых, у вас есть уязвимость sql-инъекций, которую можно устранить с помощью параметров.

Во-вторых, вы выполняете действия с базой данных в открытом хранилище данных, что может привести к многочисленным проблемам.

В-третьих, вы выполняете слишком много работы, чтобы определить, существует ли серийный номер. Вы можете использовать оператор SQL Server Exists и метод ExecuteScalar SqlCommand для возврата и тестирования одного значения, что делает код намного быстрее и проще для понимания.

Наконец, вам необходимо убедиться, что одноразовые предметы утилизируются, и самый простой / лучший способ сделать это - использовать блоки использования.

Все они могут быть решены с помощью следующего кода:

    Using connection As New SqlConnection(connStr)
        Dim sqlcheck As String = "IF EXISTS(select 1 FROM EquipmentDetail WHERE SerialNumber=@SerialNumber) SELECT 1 ELSE SELECT 0"
        Using cmd As New SqlCommand(sqlcheck, connection)
            cmd.Parameters.AddWithValue("@SerialNumber", TextBox1.Text)
            connection.Open()

            If CBool(cmd.ExecuteScalar) Then
                MessageBox.Show(TextBox1.Text & " was already added")
            Else
                Using insertCmd As New SqlCommand
                    insertCmd.Connection = connection

                    insertCmd.CommandText = "INSERT INTO EquipmentDetail (SerialNumber, BoxNumber, FATTNumber, FaultTicketNumber, Description, ProductCode)" &
                    "VALUES(@SerialNumber, @BoxNumber, @FATTNumber, @FaultTicketNumber, @Description, @ProductCode)"
                    insertCmd.Parameters.AddWithValue("@SerialNumber", TextBox1.Text)
                    insertCmd.Parameters.AddWithValue("@BoxNumber", TextBox2.Text)
                    insertCmd.Parameters.AddWithValue("@FATTNumber", TextBox3.Text)
                    insertCmd.Parameters.AddWithValue("@FaultTicketNumber", TextBox4.Text)
                    insertCmd.Parameters.AddWithValue("@Description", TextBox6.Text)
                    insertCmd.Parameters.AddWithValue("@ProductCode", ComboBox1.Text)

                    insertCmd.ExecuteNonQuery()

                    MessageBox.Show("Equipment successfully added.", "Equipment", MessageBoxButtons.OK)
                    TextBox1.Text = ""
                    TextBox2.Text = ""
                    TextBox3.Text = ""
                    TextBox4.Text = ""
                    TextBox6.Text = ""
                    TextBox1.Focus()
                End Using

            End If
        End Using
        connection.Close()
    End Using
0 голосов
/ 12 января 2012

Во-первых, вы объединяете строки для создания оператора SQL.ОЧЕНЬ опасно, читайте о внедрении SQL и параметризации.

Проблема заключается в том, что вы выполняете INSERT только в том случае, если в результате проверки SerialNumber есть строки.Но если SerialNumber нет, он ничего не сделает.Возможно, вам следует попытаться изменить оператор If следующим образом:

If read.HasRows Then

    MessageBox.Show(read("SerialNumber").ToString() & " was already added")

Else

    cmd.Connection = connection
    cmd.CommandText = "INSERT INTO EquipmentDetail (SerialNumber, BoxNumber, FATTNumber, FaultTicketNumber, Description, ProductCode)" &
      "VALUES('" & TextBox1.Text & "',  '" & TextBox2.Text & "',  '" & TextBox3.Text & "',  '" & TextBox4.Text & "', '" & TextBox6.Text & "',  '" & ComboBox1.Text & "')"
    cmd.ExecuteNonQuery()

    MessageBox.Show("Equipment successfully added.", "Equipment", MessageBoxButtons.OK)
            TextBox1.Text = ""
            TextBox2.Text = ""
            TextBox3.Text = ""
            TextBox4.Text = ""
            TextBox6.Text = ""
            TextBox1.Focus()
            connection.Close()

End If
read.Close()
0 голосов
/ 12 января 2012

Если значение SerialNumber не существует в БД, ничего не будет возвращено - поэтому блок, содержащий вашу вставку, никогда не будет достигнут.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...