2010-04-09 22 views
19

Tengo un par de vistas sql con claves primarias compuestas que quiero consultar, y dado que Hibernate hace un dolor trabajar con claves compuestas, estoy usando createSQLQuery. El problema es que este método solo puede devolver una Lista, y necesito referirme a las columnas por su índice.Usando nombres de columnas sql en hibernate createSQlquery resultado

¿Alguna posibilidad de que yo pudiera hacer algo como jdbc y referirme a las columnas por su nombre sql en lugar de su índice?

Respuesta

46
Query query=session.createSQLQuery("your query"); 
query.setResultTransformer(AliasToEntityMapResultTransformer.INSTANCE); 
List<Map<String,Object>> aliasToValueMapList=query.list(); 

Como se puede averiguar a partir del código, la lista contiene objetos de mapa que representa cada fila. Cada objeto Map tendrá el nombre de la columna como clave y el valor como valor.

Nota: Esto funciona para SQLQuery, si usa AliasToEntityMapResultTransformer en la consulta hql sin especificar alias, obtendrá el valor de índice como clave.

Si vuelve a transformar aliasToValueMapList en su lista de POJO, le aconsejo que cree su propio ResultTransformer y que devuelva su objeto personalizado del método 'transformTuple'.

+0

Por cierto, tengo una consulta sql en el formulario "select table1.price as price1 from ..." y por alguna razón el AliasToEntityMapResultTransformer no está mapeando precio1. Si lo hago, "select (table1.precio * 1) como precio1 desde ... "funciona, así que creo que encontré un error en el transformador ... – Ricardo

+0

Recuerde agregar declaraciones' addScalar' (por ejemplo 'query.addScalar (" myAlias ​​", IntegerType.INSTANCE) '). De lo contrario, puede obtener alias incorrectos (por ejemplo, convertido a mayúsculas) o tipos de datos incorrectos. –

+0

De alguna manera tengo que agregar esta importación para que funcione: import org.hibernate.transform.AliasToEntityMapResultTransformer – ian0411

1

Su pregunta es ambigua: en el primer párrafo, desea hacer referencia a las columnas por índice y, en el segundo, por el nombre sql. Dado que por índice es fácil, lo asumiré por mi nombre.

En primer lugar, puede utilizar el método doWork acceder a la conexión JDBC subyacente y manejarlo como lo haría con pura JDBC:

session.doWork(new Work() { 
    public void execute(Connection connection) throws SQLException { 
    connection.prepareStatement(... 
    } 
}); 

O bien, puede utilizar query.getReturnAliases que devuelve un String[] de la columna nombres. Para effciency, probablemente construiría un Map de alias para indexar y luego puedes hacer algo como result[map.get("column name")].

Pero en realidad, Hibernate maneja las claves compuestas con bastante facilidad cuando se utilizan asignaciones de xml (no se han intentado con las anotaciones). Hay un poco más de trabajo por adelantado y hay algunos problemas con las relaciones complejas (principalmente cuando los nombres de las claves externas no coinciden), pero una vez que crea la clase de id y la correlaciona, puede seguir con HQL/Criterios y obtener todos los beneficios de la carga diferida, se une simple, comprobación sucia, etc.

+0

@Brian, gracias! sí, quise decir acceso por nombre, no índice;) @Adi, sí, esa es la respuesta que quería, ¡gracias! – Ricardo

1

Método indicó en el comentario anterior:

query.getReturnAliases() 

no funciona para mí en realidad:

Caused by: java.lang.RuntimeException: SQL queries do not currently support returning aliases in query: 
0

que tiene el mismo problema, pero resuelto cuando he utilizado esta consulta consulta = Session.createSQLQuery ("su consulta"); query.setResultTransformer (AliasToEntityMapResultTransformer.INSTANCE);

Obtengo el resultado con el nombre del encabezado, pero tengo un nuevo problema cuando creo una nueva columna en la consulta sql Seleccione 'DCA5E3' como Shipmentcolor from Employee.class Pero en este caso tengo SHIPMENTCOLOR: "D". Cómo obtener el valor total de SHIPMENTCOLOR.

Cuestiones relacionadas