class Author { @Id @Column(name="person_id") private long id; @Column private String name; } class Article { @ManyToOne @JoinColumn(name="author_id") private Author author; } class SubmissionResult { @Id // part of @IdClass private Article article; @Id // part of @IdClass private Magazine magazine; } // dao search method: Criteria search = getSession().createCriteria(SubmissionResultBean.class) .add(Restrictions.eq("magazine.id", magazine.getId())); if (null != rating) { search.add(Restrictions.eq("rating", rating)); } if (!includeDelayed) { search.add(Restrictions.isNull("delayedUntil")); } search.setResultTransformer(Criteria.DISTINCT_ROOT_ENTITY); search.createAlias("article", "ar"); search.createAlias("ar.author", "arAuthor"); search.addOrder(Order.asc("arAuthor.name"));