我只使用HQL从表中获取选定的属性,维护非实体类对象的列表。 对于Eg。我的实体类:
@Entity
@Table(name="STUDENT")
public class Student {
@Id
@GeneratedValue(strategy=GenerationType.IDENTITY)
private Long id;
@Column(name="NAME", columnDefinition="TEXT", length="60", nullable = false)
private String name;
@ManyToOne
@JoinColumn(name = "Dept_id", nullable = false)
private Department department;
// Other fields...
// Getter-Setters
}
和非持久性DTO类只有更少的类成员(比如名字):
public class StudentDTO {
private String name;
// Getter-Setter for name
}
现在使用
public List<StudentDTO> getStudents(Long deptId) {
List<StudentDTO> students;
Query query = session.createQuery("select student.name " +
"from Student as student " +
"where Dept_id =?").setResultTransformer(new AliasToBeanResultTransformer(StudentDTO.class));
query.setString(0, Long.toString(deptId));
students = CommonUtil.castList(StudentDTO.class, query.list());
return students;
}
其中castList将任何集合转换为ArrayList。
public static <T> List<T> castList(Class<? extends T> clazz, Collection<?> c) {
List<T> resultList = new ArrayList<T>(c.size());
for(Object o: c)
resultList.add(clazz.cast(o));
return resultList;
}
抛出 org.hibernate.PropertyNotFoundException:在类上找不到0的setter ../ StudentDTO
参考Hibernate exception PropertyNotFoundException when using Transformer,我将查询更改为"select student.id as id,..."
,Long id
内StudentDTO
,但发出同样的异常,说找不到1的setter。
每个酒店都会获得Getter / Setter。请建议更改!
答案 0 :(得分:17)
当您使用AliasToBeanResultTransformer
时,您必须在alias
中声明正确的query
名称。类名称本身表示它会使用resultClass
名称将结果转换为alias
。
transformTuple
类的AliasToBeanResultTransformer
方法使用alias
名称查找resultClass (StudentDto)
的setter方法:
for (int i = 0; i < aliases.length; i++) {
String alias = aliases[i];
if(alias != null) {
setters[i] = propertyAccessor.getSetter(resultClass, alias);
}
}
为了使AliasToBeanResultTransformer
正常工作,您需要在query
中使用正确的别名。如果StudentDto
类中的媒体资源名称为name
,则应使用select student.name as name
。使用select student.name as n
将再次抛出异常。您在alias
中使用的query
名称应与DTO类中的属性名称相同。
答案 1 :(得分:4)
为select子句中的每个字段设置别名,这些字段与您在查询中设置为变换器类的持久性类中的字段名称相同,例如:
public mypersistenceclass()
{
// define constructor
public mypersistenceclass(){}
private String username;
// define setter and getter
}
public userclass()
{
...
Query query = session.createQuery("select Users.username as username ...")
.setResultTransformer(new AliasToBeanResultTransformer(mypersistenceclass.class));
...
}
答案 2 :(得分:3)
只需编写每个列名称,如下所示: 从class_name
中选择column_name作为property_name,....例如:从学生
中选择student.name 作为名称