vb.netparameter-passingmysqlcommand

How to concatenate single quote in MySQL query with VB.NET parameter?


I am making a MySQL Select query using MySQLCommand object in VB.NET were I use parameters. I am facing an issue, in my where clause, I need to put the value for the criteria into single quote, I tried to use backslash ' (\') to escape the single quote, it does not work. I used double quotes as well, same issue. Can somebody help me? Is there something specific I need to do when using the MySQLCommand object in VB.NET with parameter and want my parameter value to be in single quote into a query?

Here is the Function in which I make the MySQL query:

Public Shared Function getGeographyUnits(critere As String, valeur As String) As List(Of geography_unit)
    Dim conn As MySqlConnection = DBUtils.GetDBConnection()
    Dim rdr As MySqlDataReader
    conn.Open()
    Dim cmd As MySqlCommand = New MySqlCommand("select ID,description from geography_unit where @critere = ''@valeur''", conn)
    cmd.Parameters.AddWithValue("@critere", critere)
    cmd.Parameters.AddWithValue("@valeur", valeur)
    rdr = cmd.ExecuteReader()
    Dim geography_units As New List(Of geography_unit)
    While rdr.Read
        Dim geography_unit As New geography_unit
        Try
            geography_unit.ID = CLng(rdr("Id"))
            geography_unit.description = rdr("description")
        Catch ex As Exception
        End Try
        geography_units.Add(geography_unit)
    End While
    rdr.Close()
    conn.Close()
    Return geography_units
End Function

Actually, I want the cmdText for my query to be something like this after rendering:

select ID,description from geography_unit where critere = 'valeur'

The issue comes mainly from the fact that I am using parameter, how can I solve it?


Solution

  • You need to fix your code with something like this. But please note a couple of things.

    If the @valeur is enclosed in single quotes it is no more a parameter placeholder but a string constant and the parameter associated with the placeholder will not be used.

    The connection should always enclosed in a using statement to avoid dangerous resources consuption on the server

    If you want to have a variable list of field to which apply the valeur passed then you need to be absolutely sure that your user is not allowed to type the value for critere. You should provide some kind of control like combobox or dropdwonlist where the user could only choose between a prefixed set of values, then you can concatenate the critere variable to your sql command.

    Public Shared Function getGeographyUnits(critere As String, valeur As String) As List(Of geography_unit)
        Using conn As MySqlConnection = DBUtils.GetDBConnection()
    
            Dim sqlText As String = "select ID,description from geography_unit"
            
            conn.Open()
            If Not String.IsNullOrEmpty(critere) Then
                sqlText = sqlText & " where " & critere & " = @valeur"
            End If
            Dim cmd As MySqlCommand = New MySqlCommand(sqlText, conn)
            cmd.Parameters.Add("@valeur", MySqlDbType.VarChar).Value = valeur
            Using rdr As MySqlDataReader = cmd.ExecuteReader()
                Dim geography_units As New List(Of geography_unit)
                While rdr.Read
                    Dim geography_unit As New geography_unit
                    Try
                        geography_unit.ID = CLng(rdr("Id"))
                        geography_unit.description = rdr("description")
                    Catch ex As Exception
                    End Try
                    geography_units.Add(geography_unit)
                End While
            End Using
            ' rdr.Close() not needed when inside using
            ' conn.Close() not needed when inside using
            Return geography_units
        End Using
    End Function
    

    Also worth of note is the point in which I have used the Add method to add the parameter to the collection. The AddWithValue, while convenient, is the cause of a lot of bugs because it defines the type of the parameter looking at the argument received. This could end very badly when you pass dates or decimal numbers directly from a string.