2012-09-07 13 views
8

Vamos a empezar por conseguir este fuera del camino: estoy atascado utilizando un acceso DB MS y no puedo cambiarlo.Dapper y MS Access - Leer trabaja, Escribir no

Esto funciona bien:

using (OleDbConnection conn = ConnectionHelper.GetConnection()) 
{ 
    conn.Open(); 
    var results = conn.Query<string>(
    "select FirstName from Students where LastName = @lastName", 
    new { lastName= "Smith" } 
); 
    conn.Close(); 
} 

Esto funciona bien:

using (OleDbConnection conn = ConnectionHelper.GetConnection()) 
{ 
    OleDbCommand cmd = new OleDbCommand(
    "update Students set FirstName = @firstName, City = @city where LastName = @lastName", 
    conn 
); 
    cmd.Parameters.AddWithValue("firstName", "John"); 
    cmd.Parameters.AddWithValue("city", "SomeCity"); 
    cmd.Parameters.AddWithValue("lastName", "Smith"); 

    conn.Open(); 
    var result = cmd.ExecuteNonQuery(); 
    conn.Close(); 
} 

... Esto no se ejecuta sin errores pero establece la FirstName como "SomeCity" en el PP y la ciudad como "Juan":

using (OleDbConnection conn = ConnectionHelper.GetConnection()) 
{ 
    conn.Open(); 
    var results = conn.Query<string>(
    "update Students set FirstName = @firstName, City = @city where LastName = @lastName", 
    new { firstName = "John", city = "SomeCity", lastName = "Smith" } 
); 
    conn.Close(); 
} 

¿Alguna idea?

EDITAR LA SIGUIENTE

Dapper funciona si uso DynamicParameters:

using (OleDbConnection conn = ConnectionHelper.GetConnection()) 
{ 
    DynamicParameters parameters = new DynamicParameters(); 
    parameters.Add("firstName", "John"); 
    parameters.Add("city", "SomeCity"); 
    parameters.Add("lastName", "Smith"); 

    conn.Open(); 
    var result = conn.Query<string>(
    "update Students set FirstName = @firstName, City = @city where LastName = @lastName", 
    parameters 
); 
    conn.Close(); 
} 
+0

Eso es raro .. Voy a tener que tratar de repro ... –

+0

Nota: Sólo intentado reproducir con SQL Express 2008 y funciona bien ... –

+0

que he hecho esto con éxito con SQL Server ... así que creo que esto es con MS Access sólo – Trev

Respuesta

8

Después de algunas excavaciones, yo era capaz de encontrar una causa:

A continuación se CreateParamInfoGenerator delegado de SqlMapper de pulcro:

public static Action<IDbCommand, object> CreateParamInfoGenerator(Identity identity) 
    { 

     // code above here 
     IEnumerable<PropertyInfo> props = type.GetProperties().OrderBy(p => p.Name); 

Los puntales es su parámetro unánime que consigue re-ordenado por OrdenarPor (p => p.Name), que se mueve por adelantado de la ciudad.

new { firstName = "John", city = "SomeCity", lastName = "Smith" } 

Apoyos a continuación se añade a los parámetros IDbCommand donde el orden es importante.

Si comento hacia fuera OrdenarPor() cláusula, entonces todo funciona.

DynamicParameters También he probado e intencionalmente reordenan los atributos para mover la ciudad por adelantado:

 var parameters = new DynamicParameters(); 
     parameters.Add("city", "SomeCity"); 
     parameters.Add("firstName", "John"); 
     parameters.Add("lastName", "Smith"); 

     var result = dbConnection.Query<string>(
      "update Students set FirstName = @firstName, City = @city where LastName = @lastName", 
      parameters 
     ); 

Lo anterior no funcionó tan bien, por lo que el orden de los atributos es la razón!

Creo que se puede modificar su copia local del SqlMapper por ahora y quitar OrdenarPor() y esperar a que un veredicto oficial de Marc ...

Espero que esto ayude.

+1

Resulta que MS Access es [quisquilloso sobre el orden de los parámetros] (http://stackoverflow.com/a/1476818/47121). Intenté eliminar el código '.OrderBy (p => p.Name)' de SqlMapper y funciona ahora. También me gustaría saber por Marc o Sam si quitar este código tendría alguna implicación en otro lado. – Trev

+0

Yo tampoco lo sabía; ¡bueno saber! Y también tengo curiosidad sobre el propósito de la cláusula OrderBy(). –

+0

Según un comentario a la respuesta [aquí] (http://stackoverflow.com/a/19481354/2144390), esto ya no es un problema con la versión actual de Dapper. –

4

Tuve un problema similar, lo que hice fue use parameter names like @param1, @param2 en lugar de @ name, @ id, @ price, por lo que el orden sigue siendo el mismo sin tener que modificar el archivo SQLMapper.cs.

Algo así como

public void Update(Movie movie) 
{ 
    var sql = "UPDATE myDB.movies set [email protected], [email protected] where [email protected]"; 
    db.Execute(sql, new { param1 = movie.Title, param2 = movie.Genre, param3 = movie.ID }); 
} 
+0

Las cosas pueden haber cambiado desde la última vez que trabajó con Dapper. Según un comentario a la respuesta [aquí] (http://stackoverflow.com/a/19481354/2144390), esto ya no es un problema con la versión actual. –

+1

@GordThompson Gracias por el enlace. Estoy teniendo el mismo problema con la versión 1.13 a través de NuGet. –

+0

Tengo el mismo problema en 1.50.2 – RobinAtTech