简体   繁体   中英

Dynamic SQL Query With VB.net Variables String condition

Hi All probably a quick answer but I'm banging my head on this one thinking there must be a better way.

I have 4 strings if the condition of the string is not null or empty I add it to the query but the first will always not need the AND so I've added WHERE 1 = 1 then I can add an AND ID = @ID etc so all four can be added. What am I missing?

   Dim sqlBuilder As New StringBuilder()
    '1 = 1 allows an and.
    sqlBuilder.Append("SELECT * FROM table WHERE 1=1 ")

    If Surname <> "" Then
        sqlBuilder.Append(" AND Surname=@surname")
    End If
    If Payroll <> "" Then
        sqlBuilder.Append(" AND payroll = @payroll")
    End If
    If VehicleReg <> "" Then
        sqlBuilder.Append(" AND registration = @registration")
    End If
    If OrgID > 0 Then
        sqlBuilder.Append(" AND OrganisationID = @orgid")
    End If

There's an easy way to use a single, unchanging SQL query while making parameters optional, eg

Dim query = "SELECT * FROM Person WHERE (@FirstName IS NULL OR FirstName = @FirstName) AND (@LastName IS NULL OR LastName = @LastName)"
Dim command As New SqlCommand

command.CommandText = query

With command.Parameters
    .Add("@FirstName", SqlDbType.VarChar, 50).Value = If(firstNameTextBox.TextLength = 0, CObj(DBNull.Value), firstNameTextBox.Text)
    .Add("@LastName", SqlDbType.VarChar, 50).Value = If(lastNameTextBox.TextLength = 0, CObj(DBNull.Value), lastNameTextBox.Text)
End With

By setting a parameter to NULL you effectively ignore it. For instance, if the @FirstName parameter is set to NULL then @FirstName IS NULL is true and that first set of criteria matches every row, otherwise it only matches those rows that contain the specified first name. Similarly for the second set of criteria. You can do the same thing for as many sets of criteria as you like, comparing the parameter to NULL or the column to the parameter.

One point to note is that I have used two parameters for four criteria in the example above. That is possible because SqlClient supports genuine named parameters. With providers that don't support genuine named parameters, eg Jet or ACE with OleDb , you actually need to add twice as many parameters because you can't use the same parameter twice in the SQL code, eg

Dim query = "SELECT * FROM Person WHERE (@FirstName1 IS NULL OR FirstName = @FirstName2) AND (@LastName1 IS NULL OR LastName = @LastName2)"
Dim command As New OleDbCommand

command.CommandText = query

Dim firstName = If(firstNameTextBox.TextLength = 0, CObj(DBNull.Value), firstNameTextBox.Text)
Dim lastName = If(lastNameTextBox.TextLength = 0, CObj(DBNull.Value), lastNameTextBox.Text)

With command.Parameters
    .Add("@FirstName1", SqlDbType.VarChar, 50).Value = firstName
    .Add("@FirstName2", SqlDbType.VarChar, 50).Value = firstName
    .Add("@LastName1", SqlDbType.VarChar, 50).Value = lastName
    .Add("@LastName2", SqlDbType.VarChar, 50).Value = lastName
End With

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM