I've found the following piece of code in an application I have to maintain
def addCriteriaClosure = { criteriaList ->
criteriaList.inList('id', paketInstance.dateien.id)
}
def criteria = Datei.createCriteria()
def result = criteria.list() {
addCriteriaClosure.call(criteria)
}
Sadly, this call results in the following error:
java.sql.SQLSyntaxErrorException: ORA-01795: maximum number of expressions in a list is 1000
Fact is that paketInstance.dateien
contains more then 1000 rows / items.
To avoid this error I've tried the following approach:
def addCriteriaClosure = { criteriaList ->
paketInstance.dateien.asList().collate(999).each {
criteriaList.inList('id', paketInstance.dateien.asList().collate(999).id)
}
}
but this results in this error:
java.lang.ClassCastException: java.util.ArrayList cannot be cast to java.lang.Long
I know that the solution is to use the collate(999)
operation, but I don't know how to combine it with the initial approach to get the expected result.
Edit #1
Unfortunatly I can not edit this part of the implementation:
def criteria = [Type].createCriteria()
def result = criteria.list() {
addCriteriaClosure.call(criteria)
}
Where the concrete type gets passed in to the method.
I only can edit the definition of the addCriteriaClosure
For example:
def addCriteriaClosure = { criteriaList ->
criteriaList.inList('id', paketInstance.dateien.id)
}
Edit #2
When I design my criteria closure like following
def l = paketInstance.dateien.id.toList().collate(999)
def addCriteriaClosure = { criteriaList ->
l.each {
a -> criteriaList.inList("id", a.toList())
}
}
Hibernate creates an SQL-Statement which splits the lists into to seperate in
WHERE clauses. But the problem is that these two clauses are linked with an AND
. To get the right result I need the OR
for the two lists, not the AND
in the generated sql
produced SQL:
select this_.id as id51_0_, this_.version as version51_0_, this_.aktualisiert_am as aktualis3_51_0_, this_.name as name51_0_, this_.nummer as nummer51_0_, this_.pfad as pfad51_0_, this_.status as status51_0_, this_.typ as typ51_0_ from datei this_ where this_.id in (?, ?, ?, ?, ?, ?....) and this_.id in (?, ?, ?, ?, ?, ?, ?....)
So Instead of and this_.id
in I need or this_.id in
Found a solution
def collatedFileList = paketInstance.dateien.id.toList().collate(999)
def addCriteriaClosure = { criteriaList ->
criteriaList.or {
collatedFileList.each {
l -> criteriaList.inList("id", l.toList())
}
}
}