使用休眠标准连接复合键

时间:2014-12-05 06:56:08

标签: java sql hibernate hibernate-criteria composite-key

我没有得到如何编写Hibernate条件查询来实现类似于下面SQL查询获得的结果的结果。请告诉我实现结果需要遵循的步骤。

SELECT PRODUCT.PRODUCTNAME, ITEM.ITEMNAME 
FROM PRODUCT_ITEM
JOIN PRODUCT
   ON PRODUCT_ITEM.ID = PRODUCT.ID
JOIN ITEM
   ON PRODUCT_ITEM.ID = ITEM.ID

上面是我的Sql Query,用于获取product_name和item_name。它工作正常。 我尝试使用HIBERNATE CRITERIA QUERY获得相同的结果。

Criteria criteria = session.createCriteria(ProductItem.class,"pi");
criteria.createAlias("pi.pk.product", "pip");
criteria.createAlias("pi.pk.item", "pii");
criteria.setProjection(Projections.projectionList().add(Projections.property("pip.id")).add(Projections.property("pii.id")));

List<Object[]> list = criteria.list();

我收到错误说

Exception in thread "main" org.hibernate.exception.SQLGrammarException: could not execute query
at org.hibernate.exception.SQLStateConverter.convert(SQLStateConverter.java:67)
at org.hibernate.exception.JDBCExceptionHelper.convert(JDBCExceptionHelper.java:43)
at org.hibernate.loader.Loader.doList(Loader.java:2147)
at org.hibernate.loader.Loader.listIgnoreQueryCache(Loader.java:2028)
at org.hibernate.loader.Loader.list(Loader.java:2023)
at org.hibernate.loader.criteria.CriteriaLoader.list(CriteriaLoader.java:95)
at org.hibernate.impl.SessionImpl.list(SessionImpl.java:1569)
at org.hibernate.impl.CriteriaImpl.list(CriteriaImpl.java:283)
at checkComposite.main(checkComposite.java:38)
Caused by: org.postgresql.util.PSQLException: ERROR: missing FROM-clause entry for table "pip1_"
Position: 8
at org.postgresql.core.v3.QueryExecutorImpl.receiveErrorResponse(QueryExecutorImpl.java:2198)
at org.postgresql.core.v3.QueryExecutorImpl.processResults(QueryExecutorImpl.java:1927)
at org.postgresql.core.v3.QueryExecutorImpl.execute(QueryExecutorImpl.java:255)
at org.postgresql.jdbc2.AbstractJdbc2Statement.execute(AbstractJdbc2Statement.java:561)
at org.postgresql.jdbc2.AbstractJdbc2Statement.executeWithFlags(AbstractJdbc2Statement.java:419)
at org.postgresql.jdbc2.AbstractJdbc2Statement.executeQuery(AbstractJdbc2Statement.java:304)
at org.hibernate.jdbc.AbstractBatcher.getResultSet(AbstractBatcher.java:186)
at org.hibernate.loader.Loader.getResultSet(Loader.java:1668)
at org.hibernate.loader.Loader.doQuery(Loader.java:662)
at org.hibernate.loader.Loader.doQueryAndInitializeNonLazyCollections(Loader.java:224)
at org.hibernate.loader.Loader.doList(Loader.java:2144)

我的ENTITYS如下所示。

@Entity
@Table(name = "item")
public class Item {
private Integer id;
private String name;
private List<ProductItem> productItems = new LinkedList<ProductItem>();

public Item() {
}

@Id
@GenericGenerator(name = "generator", strategy = "increment")
@GeneratedValue(generator = "generator")
@Column(name = "item_id", nullable = false)
public Integer getId() {
    return this.id;
}

public void setId(Integer id) {
    this.id = id;
}

@Column(name = "name")
public String getName() {
    return this.name;
}

public void setName(String name) {
    this.name = name;
}

@OneToMany(fetch = FetchType.LAZY, mappedBy = "pk.item")
public List<ProductItem> getProductItems() {
    return this.productItems;
}

public void setProductItems(List<ProductItem> productItems) {
    this.productItems = productItems;
}
}

产品实体

@Entity
@Table(name = "product")
public class Product {

private Integer id;
private String name;
private List<ProductItem> productItems = new LinkedList<ProductItem>();

public Product() {
}

@Id
@GenericGenerator(name = "generator", strategy = "increment")
@GeneratedValue(generator = "generator")
@Column(name = "product_id", nullable = false)
public Integer getId() {
    return this.id;
}

public void setId(Integer id) {
    this.id = id;
}

@Column(name = "name")
public String getName() {
    return this.name;
}

public void setName(String name) {
    this.name = name;
}

@OneToMany(fetch = FetchType.LAZY, mappedBy = "pk.product")
public List<ProductItem> getProductItems() {
    return this.productItems;
}

public void setProductItems(List<ProductItem> productItems) {
    this.productItems = productItems;
}
}

PRODUCT_ITEM实体。

@Entity
@Table(name = "product_item")
@AssociationOverrides({
@AssociationOverride(name = "pk.item", joinColumns = @JoinColumn(name = "item_id")),
@AssociationOverride(name = "pk.product", joinColumns = @JoinColumn(name = "product_id"))
    })
public class ProductItem {

private ProductItemPk pk = new ProductItemPk();

@EmbeddedId
private ProductItemPk getPk() {
    return pk;
}

private void setPk(ProductItemPk pk) {
    this.pk = pk;
}

@Transient
public Item getItem() {
    return getPk().getItem();
}

public void setItem(Item item) {
    getPk().setItem(item);
}

@Transient
public Product getProduct() {
    return getPk().getProduct();
}

public void setProduct(Product product) {
    getPk().setProduct(product);
}

public boolean equals(Object o) {
    if (this == o) return true;
    if (o == null || getClass() != o.getClass()) return false;

    ProductItem that = (ProductItem) o;

    if (getPk() != null ? !getPk().equals(that.getPk()) : that.getPk() != null) return false;

    return true;
}

public int hashCode() {
    return (getPk() != null ? getPk().hashCode() : 0);
}
}

Embedable Class如下。

@Embeddable
public class ProductItemPk implements Serializable {

private Item item;
private Product product;

@ManyToOne
public Item getItem() {
    return item;
}

public void setItem(Item item) {
    this.item = item;
}

@ManyToOne
public Product getProduct() {
    return product;
}

public void setProduct(Product product) {
    this.product = product;
}

public boolean equals(Object o) {
    if (this == o) return true;
    if (o == null || getClass() != o.getClass()) return false;

    ProductItemPk that = (ProductItemPk) o;

    if (item != null ? !item.equals(that.item) : that.item != null) return false;
    if (product != null ? !product.equals(that.product) : that.product != null)
        return false;

    return true;
}

public int hashCode() {
    int result;
    result = (item != null ? item.hashCode() : 0);
    result = 31 * result + (product != null ? product.hashCode() : 0);
    return result;
}
}

1 个答案:

答案 0 :(得分:0)

尝试将查询更改为:

Criteria criteria = session.createCriteria(ProductItem.class,"pi");
criteria.createAlias("pi.pk", "pipk");
criteria.createAlias("pipk.product", "pip");
criteria.createAlias("pipk.item", "pii");
criteria.setProjection(Projections.projectionList().add(Projections.property("pip.id")).add(Projections.property("pii.id")));
List<Object[]> list = criteria.list();