eine CASE-Anweisung in HQL Mit wählen
-
19-08-2019 - |
Frage
Gibt es eine Möglichkeit, die folgenden in HQL zu tun:
SELECT
case when flag = true then SUM(col1) else SUM(col2)
FROM
myTable
Andere Tipps
Anscheinend ist die Fähigkeit, dies zu tun, wurde in 3.0.4 hinzugefügt , mit der Einschränkung, dass Sie nicht Unter wählen in der else-Klausel verwenden können.
Siehe Hibernate-Forum: https://forum.hibernate.org/viewtopic.php ? t = 942197
Antwort vom Team (Gavin): Fall ist in der where-Klausel unterstützt, aber nicht in der select-Klausel in HB3.
Und mit Staat in JIRA gesehen "Ungelöst".
Im folgenden finden Sie eine Arbeits Abfrage finden (Hibernate auf postgresql), die verwendet 2 case-Anweisungen einen Booleschen Wert mit der entsprechenden Textdarstellung zu ersetzen.
SELECT CASE ps.open wahr, wenn THEN 'AUF' else 'CLOSED' END CASE ps.full WENN wahr THEN 'FULL' else 'FREE' END, ps.availableCapacity VON ParkingState als ps
Wir verwenden HQL Abfrage ausgiebig überwintern und ich denke, schließlich gibt es einen hackish Weg ist, so etwas zu tun:
Unter der Annahme, wir hatten ursprünglich eine Abfrage von
i2.element.id = :someId
entschieden Dann zu erweitern diese um so etwas zu sein:
((i.element.id = :someId and i2.element.id=:someId) or (i2.element.id = :someId))
Aber es gab ein Problem, bei dem wir es nur Lookup für diese auf Classtype basiert wollen so eine case-Anweisung:
(case when type(i)=Item then
((i.element.id = :someId and i2.element.id=:someId) or (i2.element.id = :someId))
else
i.element.id = :someId
end)
Vor nicht funktionieren Sie eine einfache Version von oben Arbeit machen könnten, indem Sie:
(case when type(i)=Item then
i2.element.id
else
i.element.id
end)=:elementId
Aber das eigentlich nicht tun, was wir brauchen, es zu tun, wir wollen es genau obige Abfrage zu tun, also zu wissen, Sie in eine Variable am Ende einer case-Anweisung zuweisen können, wo wenig HQL:
(
(
(case when
type(r)=Item then
i.element.id
else
i.element.id end) = :elementId
and
(case when
type(r)=Item then
i2.element.id
else
i.element.id end) = :elementId
)
or
(case when
type(r)=Item then
i2.element.id
else
i.element.id end) = :elementId
)
Ich habe es geschafft, die Abfrage nun anhand von Case-Anweisung funktioniert, sicher, dass es viel mehr langatmig aber tatsächlich tut das gleiche wie die erste Instanz
ich vor dem gleichen Problem in HQL dann löste ich die folgende Abfrage ist
select CONCAT(event.address1,', ', CASE WHEN event.address2 IS NULL THEN '' ELSE concat(event.address2,', ') END, event.city from EventDetail event where event.startDate>=:startDate and event.endDate<=:endDate;
Dies ist ein Beispiel eines String-Vergleich in der Bedingung verwenden:
SELECT CASE f.type WHEN 'REMOVE'
THEN f.previousLocation
ELSE f.currentLocation
END
FROM FileOperation f