Hibernate version: 3.2.5-ga
Name and version of the database you are using: MySql 5.0.45
I'm using the following model:
Code:
package com.dummy.model;
import java.io.Serializable;
import java.util.HashMap;
import java.util.Map;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Inheritance;
import javax.persistence.InheritanceType;
import javax.persistence.JoinColumn;
import javax.persistence.JoinTable;
import javax.persistence.Table;
import org.hibernate.annotations.CollectionOfElements;
import org.hibernate.annotations.MapKey;
/**
* Dummy Model
*/
@Entity
@Table(name = "dummytable")
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public class MapTest implements Serializable {
private static final long serialVersionUID = 1L;
@Id
@GeneratedValue(strategy = GenerationType.AUTO)
private Long metaId;
@Column(nullable = true)
private String exampleKey;
// more attributes here
@CollectionOfElements
@JoinTable(name = "criteriamap", joinColumns = @JoinColumn(name = "item_id"))
@MapKey(columns = @Column(name = "key_criterion"))
@Column(name = "value_criterion")
private Map<String, String> criteriaMap = new HashMap<String, String>();
public Map<String, String> getCriteriaMap() {
return criteriaMap;
}
public void setCriteriaMap(Map<String, String> criteriaMap) {
this.criteriaMap = criteriaMap;
}
public Long getMetaId() {
return metaId;
}
public void setMetaId(Long metaId) {
this.metaId = metaId;
}
public String getExampleKey() {
return exampleKey;
}
public void setExampleKey(String exampleKey) {
this.exampleKey = exampleKey;
}
// more getters and setters here
}
The criteriaMap is used to store user defined data which is entered by the end-user in a GUI.
To access this data i want to use HQL as i do with all other fields:
Code:
private Map<String, Object> buildSearchCriteria(final MapTest mapTest, final StringBuilder query) {
// ...
if (mapTest.getExampleKey() != null) {
query.append(getOperator(opCount)).append(" objectAlias.exampleKey = :exampleKey");
opCount++;
paramMap.put("exampleKey", mapTest.getExampleKey());
}
// ...
}
private String getOperator(final int opCount) {
if (opCount > 0) {
return " AND";
} else {
return " WHERE";
}
}
This works fine.
My idea to access the
HashMap is as follows:
Code:
private Map<String, Object> buildSearchCriteria(final MapTest mapTest, final StringBuilder query) {
// ...
if (mapTest.getCriteriaMap() != null && mapTest.getCriteriaMap().size() > 0) {
int i=0;
for (String key : mapTest.getCriteriaMap().keySet()) {
query.append(getOperator(opCount)).append(" key_criterion= :keyName"+i).append(" AND value_criterion = :valueName"+i);
opCount++;
paramMap.put("keyName"+i, key);
paramMap.put("valueName"+i, mapTest.getCriteriaMap().get(key));
i++;
}
}
// ...
}
This doesn't work, because Hibernate doesn't know the key_criterion and the value_criterion columns defined by the model.
I tried to qualify both columns by objectAlias.* or by objectAlias.criteriaMap.*, both attempts didn't work either.
Scanning the HashMap in Java code is not an option, because the database is to big to load to memory and speed is very important.
So, I'm looking for a solution based on HQL.
Thank you for your help.