如何避免hibernate中的字符串成员?

时间:2016-04-15 09:24:27

标签: java hibernate java-ee hibernate-criteria

是否可以避免在Hibernate中使用字符串升级,例如在标准限制和预测中:

Criteria criteria = session.createCriteria(Employee.class)
                   .add(Restrictions.eq("name", "john doe"));

Projection p1 = Projection.property("name");

例如,在上面的代码段中,将"name"替换为something.name ,其中something包含Employee类的所有成员。

这样可以减少错误,例如字符串中的拼写错误。

编辑:更新问题更一般,而不仅仅是标准。

3 个答案:

答案 0 :(得分:3)

您可以打开JPA的Metamodel生成,并使用Criteria API将生成的类字段用作类型和名称-safe“literals”。 来自Hibernate docs

的示例
@Entity
public class Order {
    @Id
    @GeneratedValue
    Integer id;

    @ManyToOne
    Customer customer;

    @OneToMany
    Set<Item> items;
    BigDecimal totalCost;
    // standard setter/getter methods
}

@StaticMetamodel(Order.class) // <<<<<<<<<< this class gets generated for you
public class Order_ {
    public static volatile SingularAttribute<Order, Integer> id;
    public static volatile SingularAttribute<Order, Customer> customer;
    public static volatile SetAttribute<Order, Item> items;
    public static volatile SingularAttribute<Order, BigDecimal> totalCost;
}
// type-safe and typo-proof building of query:
CriteriaBuilder cb = entityManager.getCriteriaBuilder();
CriteriaQuery<Order> cq = cb.createQuery(Order.class);
SetJoin<Order, Item> itemNode = cq.from(Order.class).join(Order_.items);
cq.where( cb.equal(itemNode.get(Item_.id), 5 ) ).distinct(true);

在大型实体和复杂查询的情况下,它非常方便。唯一的缺点是,有时使用它会变得非常冗长 它是JPA标准,因此EclipseLink和其他JPA提供商也支持它。

答案 1 :(得分:1)

您可以创建一个Employee Constants类:

public class EmployeeConstants {
        public static final String firstName= "firstname";
        public static final String lastName= "lastname";
        ....
}

并将该字段称为:

Criteria criteria = session.createCriteria(Employee.class)
                   .add(Restrictions.eq(EmployeeConstants.firstName, "john doe"));

实际上EmployeeConstants.firstName会返回firstnameEmployee必须是doAnswer(new Answer<String>() { @Override public String answer(InvocationOnMock invocation) throws Throwable { return "String"; } }).when(object).voidMethod(); Assert.assertEquals("String",object.voidMethod()); 实体的字段名称。

答案 2 :(得分:0)

在您的情况下,您可以通过示例使用查询:

Employee employee = new Employee();
employee.setName("john doe");
Example employeeExample = Example.create(employee);

Criteria criteria = session.createCriteria(Employee.class).add(employeeExample);