I would like a Criteria query to instantiate a DTO class using an AliasToBeanResultTransformer. The goal is to produce a light weight paged list with IDs for further action for a home page. This calls for a reporting type query.
Criteria crit = session.createCriteria(Profile.class);
crit.createAlias("personalData", "pd");
crit.createAlias("emails", "e");
crit.createAlias("telephones", "t");
ProjectionList properties = Projections.projectionList();
properties.add(Projections.property("id").as( "id"));
properties.add(Projections.property("pd.lastName").as("lastName"));
properties.add(Projections.property("pd.fullName").as("fullName"));
properties.add(Projections.property("e.emailAddress").as("email"));
properties.add(Projections.property("t.phoneNumber").as("phone"));
crit.setProjection(properties);
crit.setResultTransformer(new AliasToBeanResultTransformer(ProfileDTO.class));
profiles = crit.list();
This fails to instantiate my DTO class. ProfileDTO has a matching constructor:
public ProfileDTO(Long id, String lastName, String fullName, String email,
String phone) {
this(id,fullName);
this.lastName = lastName;
this.email = email;
this.phone = phone;
}
And the query works when I construct ProfileDTO objects manually with the result rows
List<Object[]> rows = crit.list();
for ( Object[] row: rows ) {
ProfileDTO dto = new ProfileDTO();
dto.setId((Long)row[0]);
dto.setLastName((String)row[1]);
dto.setFullName((String)row[2]);
dto.setEmail((String)row[3]);
dto.setPhone((String)row[4]);
profiles.add(dto);
}
My workaround is working fine, but it seems unnecessary. What am I doing wrong?
try with this:
The AliasToBeanResultTransformer uses setters to populate the DTO. If you want to use a constructor, to create your bean instance, you need to use an AliasToBeanConstructorResultTransformer.
Your DTO seems to have a setter for all the elements of the tuple, except for lastName. Maybe this is the problem.
That said, your code as is is simple, easy to maintain, and refactorable. It wouldn't be refactorable with an AliasToBeanResultTransformer. I generally prefer to instantiate my DTOs myself, just as you did.