Conversion de SQL en HQL [fermé]
Question
J'essaie de convertir la requête SQL ci-dessous en HQL et j'ai quelques problèmes. Une conversion ligne par ligne ne fonctionne pas, je me demande si je devrais utiliser une jointure interne dans le HQL?
SELECT (UNIX_TIMESTAMP(cosc1.change_date) - UNIX_TIMESTAMP(cosc2.change_date))
FROM customer_order_state_change cosc1
LEFT JOIN customer_order_state cos1_new on cosc1.new_state_id = cos1_new.customer_order_state_id
LEFT JOIN customer_order_state cos1_old on cosc1.old_state_id = cos1_old.customer_order_state_id
LEFT JOIN customer_order_state_change cosc2 on cosc2.customer_order_id = cosc1.customer_order_id
LEFT JOIN customer_order_state cos2_new on cosc2.new_state_id = cos2_new.customer_order_state_id
LEFT JOIN customer_order_state cos2_old on cosc2.old_state_id = cos2_old.customer_order_state_id
WHERE cos1_new.name = "state1" AND cos2_new.name = "state2" and cosc2.change_date < "2008-11-06 09:00"
AND cosc2.change_date > "2008-11-06 06:00" GROUP BY cosc1.change_date, cosc2.change_date ;
La requête renvoie le temps en secondes entre les changements d'état pour une commande client.
Les noms d'état et les dates sont insérés dynamiquement dans la requête.
Modifier: Je viens d'essayer cela
"SELECT (UNIX_TIMESTAMP(cosc1.changeDate) - UNIX_TIMESTAMP(cosc2.changeDate))" +
" FROM" +
" " + CustomerOrderStateChange.class.getName() + " as cosc1" +
" INNER JOIN " + CustomerOrderStateChange.class.getName() + " as cosc2" +
" WHERE cosc1.newState.name = ?" +
" AND cosc1.order.id = cosc2.order.id" +
" AND cosc2.newState.name = ?" +
" AND cosc2.changeDate < ?" +
" AND cosc2.changeDate > ?" +
" GROUP BY cosc1.changeDate, cosc2.changeDate";
et l'exception reçue " une jointure externe ou complète doit être suivie d'une expression de chemin "
La solution
En général, les jointures HQL sont spécifiées à l'aide de la propriété de l'objet, par exemple, si la classe Foo, Bar et Foo.bar est de type Bar, alors de Foo f joint interne f.bar en tant que b
est la jointure. Autant que je sache, il n’ya aucun moyen de créer une auto-jointure dans HQL (je peux me tromper ici).
Cela dit, Hibernate vous permet d’écrire (légèrement amélioré) des requêtes SQL avec session.createSQLQuery (...)
.
Autres conseils
Nous avons fini par changer pour utiliser le SQL natif et un PreparedStatement car il semble que la session.createSQLQuery () d'Hibernate ne fonctionne que pour les entités gérées.