Java 使用Projecions从子表中获取特定列

Java 使用Projecions从子表中获取特定列,java,mysql,hibernate,projection,Java,Mysql,Hibernate,Projection,我有两张桌子 Loan (id, amount, duration) LoanStatus(id, status, loan_id) // just an example, but it has lot more fields in this table Loan.java public class Loan{ private int id; private int amount; private int duration; private LoanSt

我有两张桌子

Loan (id, amount, duration)

LoanStatus(id, status, loan_id)   // just an example, but it has lot more fields in this table
Loan.java

public class Loan{

    private int id;
    private int amount;
    private int duration;
    private LoanStatus loanStatus;

    // getter and setters

}
LoanStatus.java

public class LoanStatus{   // just an example, but it has many fields than what actually given

    private int id;
    private String status;
    private Loan loan;

    //getter and setters

}
现在,我只想使用投影获取
金额
持续时间
贷款状态
。我已使用
createAlias()
成功获取该特定列,但将其设置为setter时会出现问题

Criteria criteria = getSession().createCriteria(Loan.class,"loan");
    criteria.createAlias("loan.loanStatus", "loanStatus")
            .setProjection(Projections.projectionList().add(Projections.property("id"),"id")
            .add(Projections.property("amount"),"amount")
            .add(Projections.property("duration"),"duration")
            .add(Projections.property("loanStatus.status"), "loanStatus"))
            .add(Restrictions.eq("id", id))
            .setResultTransformer(Transformers.aliasToBean(Loan.class));
    return criteria.list();
我有一个错误,如下所示

IllegalArgumentException occurred while calling setter for property [com.site.dto.Loan.loanStatus (expected type = com.site.dto.LoanStatus)]; target = [com.site.dto.Loan@4083974a], property value = [Pending]

因此,我得到了预期的列值“Pending”,但问题是在将其设置为setter时。我见过很多关于投影的问题,但大多数问题都是基于使用投影的限制,而不是使用投影获取孩子的特定列。

编写自己的自定义转换器。下面的实现可能正是您所需要的

。在他们的文档中编写的使用示例

class Person {
  private Long id;
  private String name;
  private Car car;
  // getters and setters
}

class Car {
  private Long id;
  private String color;
  // getters and setters
}

List<Person> getPeople() {
  ProjectionList projections = Projections.projectionList()
    .add(Projections.id().as("id"))
    .add(Projections.property("name").as("name"))
    .add(Projections.property("c.id").as("car.id"))
    .add(Projections.property("c.color").as("car.color"));

  Criteria criteria = getCurrentSession().createCriteria(Person.class)
    .createAlias("car", "c")
    .setProjection(projections)
    .setResultTransformer(new AliasToBeanNestedResultTransformer(Person.class));

  return (List<Person>) criteria.list();
}

// each car of Person will be populated
班级人员{
私人长id;
私有字符串名称;
私家车;
//接球手和接球手
}
班车{
私人长id;
私有字符串颜色;
//接球手和接球手
}
列出getPeople(){
ProjectionList projections=projections.ProjectionList()
.add(Projections.id().as(“id”))
.add(Projections.property(“名称”)。作为(“名称”))
.添加(投影。属性(“c.id”)。作为(“汽车id”))
添加(投影属性(“c.color”)为(“汽车颜色”);
Criteria=getCurrentSession().createCriteria(Person.class)
.createAlias(“汽车”、“c”)
.setProjection(投影)
.setResultTransformer(新别名TobeanNestedResultTransformer(Person.class));
返回(列表)条件。列表();
}
//每辆车的人都会有人

但恰恰相反,我将loanStatus作为loan类中的一个对象,用于一对一映射,也用于基于状态的简单限制。坦率地说,我只需要loanStatus对象中的status字段,但它应该作为loanStatus对象而不是字符串提供,因为我有一些进一步的jaxb XML转换我编辑了一个答案,没有注意到Loan类也是一个实体,我认为它是一个简单的数据传输对象谢谢。。我也想过。但我在loan status中有很多状态,所以我认为为每个状态创建临时字段不是一个好的做法。我只是想知道是否可以将子对象的特定字段作为子对象,而不是在父对象中生成临时字段。例如,如果我调用loan.getLoanStatus().getStatus(),它应该返回status。但如果我调用loan.getLoanStatus().getSomeOtherFields(),它应该返回null。这是我的预期输出。就像使用投影只获取父表中的少数列一样,我也应该能够在子对象中仅获取所需的列,而不是作为父对象中的字段。我打算建议编写一个自定义转换器,并在线发现了一个实现,您很可能可以按原样使用它