package com.qcadoo.model.internal.search;
import java.util.ArrayList;
import org.hibernate.Criteria;
import org.hibernate.EntityMode;
import org.hibernate.HibernateException;
import org.hibernate.criterion.CriteriaQuery;
import org.hibernate.criterion.Criterion;
import org.hibernate.engine.TypedValue;
import org.hibernate.type.CompositeType;
import org.hibernate.type.Type;
import org.hibernate.util.StringHelper;
public class InExpressionIgnoringCase implements Criterion {
private final String propertyName;
private final Object[] values;
public InExpressionIgnoringCase(String propertyName, Object[] values) {
this.propertyName = propertyName;
this.values = values;
}
public String toSqlString(Criteria criteria, CriteriaQuery criteriaQuery) throws HibernateException {
String[] columns = criteriaQuery.findColumns(this.propertyName, criteria);
final String[] wrappedLowerColumns = wrapLower(columns);
String cols;
if (!criteriaQuery.getFactory().getDialect().supportsRowValueConstructorSyntaxInInList() && columns.length > 1) {
cols = " ( " + StringHelper.join(" = lower(?) and ", wrappedLowerColumns) + "= lower(?)) ";
cols = this.values.length > 0 ? StringHelper.repeat(cols + "or ", this.values.length - 1) + cols : "";
cols = " ( " + cols + " ) ";
return cols;
} else {
cols = StringHelper.repeat("lower(?), ", columns.length - 1) + "lower(?)";
if (columns.length > 1) {
cols = '(' + cols + ')';
}
String params = this.values.length > 0 ? StringHelper.repeat(cols + ", ", this.values.length - 1) + cols : "";
String cols1 = StringHelper.join(", ", wrappedLowerColumns);
if (columns.length > 1) {
cols1 = '(' + cols1 + ')';
}
return cols1 + " in (" + params + ')';
}
}
public TypedValue[] getTypedValues(Criteria criteria, CriteriaQuery criteriaQuery) throws HibernateException {
ArrayList list = new ArrayList();
Type type = criteriaQuery.getTypeUsingProjection(criteria, this.propertyName);
if (type.isComponentType()) {
CompositeType actype = (CompositeType) type;
Type[] types = actype.getSubtypes();
for (int j = 0; j < this.values.length; ++j) {
for (int i = 0; i < types.length; ++i) {
Object subval = this.values[j] == null ? null : actype.getPropertyValues(this.values[j], EntityMode.POJO)[i];
list.add(new TypedValue(types[i], subval, EntityMode.POJO));
}
}
} else {
for (int j = 0; j < this.values.length; ++j) {
list.add(new TypedValue(type, this.values[j], EntityMode.POJO));
}
}
return (TypedValue[]) ((TypedValue[]) list.toArray(new TypedValue[list.size()]));
}
public String toString() {
return this.propertyName + " in (" + StringHelper.toString(this.values) + ')';
}
private String[] wrapLower(final String[] columns) {
final String[] wrappedColumns = new String[columns.length];
for (int i = 0; i < columns.length; i++) {
wrappedColumns[i] = "lower(" + columns[i] + ")";
}
return wrappedColumns;
}
}