Criteria Query en Hibernate

Uno de los puntos débiles que encontré en el nuevo estándar JPA (Java Persistence API de Sun), es que no provee una funcionalidad análoga al Criteria Query de Hibernate.

El Criteria Query nos permite definir consultas con un estilo orientado a objetos, muy distinto al clásico SQL o HQL. La primera impresión del API me resultó un poco extraña, difícil de leer. Por ejemplo, el siguiente query con Criteria:

List personas = sess.createCriteria(Persona.class)
 .add(Restrictions.like("nombre", "Fede%"))
 .add(Restrictions.isNull("edad"))
 .addOrder(Order.asc("nombre"))
 .list();
Sería equivalente a este otro con HQL:
String query = "from Persona where nombre like 'Fede%' and edad is not null order by nombre asc";
List personas = sess.createQuery(query).list();

Sin dudas el query HQL es mas fácil de leer a simple vista, la versión orientada a objetos requiere un análisis mas detallado.
Pero por otro lado, que sucedería si la consulta tuviera que armarse dinámicamente?
Por ejemplo, si el usuario selecciona las opciones por las cuales desea realizar la búsqueda, entonces el "where" del query debemos establecerlo en tiempo de ejecución. En éste caso es dónde personalmente le encuentro una gran ventaja al Criteria porque podemos hacer cosas como:
Criteria criteria = sess.createCriteria(Persona.class);
if (nombre != null) {
criteria.add(Restrictions.eq("nombre", nombre));
}
if (edad != null) {
criteria.add(Restrictions.eq("edad", edad));
}
if (pais != null) {
criteria.add(Restrictions.eq("pais", pais));
}
List personas = criteria.list();
El código anterior define una consulta que toma como entidad base a "Persona" y luego dependiendo de si hay un valor asignado para nombre, edad y país agrega las restricciones al Criteria.

Para resolverlo en HQL deberíamos armar el query concatenando strings, que no está mal, pero puede inducir a errores en la definición, me parece que en estos casos es mas natural usar el estilo orientado a objetos del Criteria.

Además permite desarrollar un esquema de consultas genérico, donde el usuario del sistema "arma" su propio query sin mayor esfuerzo por parte del desarrollador, en próximos posts publicaré ejemplos.

No hay comentarios.: