获取JPA @OneToMany集合返回空

Kir*_*han 6 java jpa eclipselink java-ee

我正在使用Glassfish4(EclipseLink)+ JavaDB 在Action示例中尝试一些EJB3.所以我有以下关系

@Entity
@Table(name = "ITEMS")
public class Item implements Serializable {
    private static final long serialVersionUID = 1L;

    private Long itemId;
    ...
    private List<Bid> bids= new ArrayList<>();

    @Id
    @Column(name="ITEM_ID")
    public Long getItemId() {
        return itemId;
    }

    public void setItemId(Long itemId) {
        this.itemId = itemId;
    }

    @OneToMany(mappedBy="item",fetch=FetchType.EAGER)   
    @JoinColumn(name="BID_ITEM_ID",referencedColumnName="ITEM_ID")
    public List<Bid> getBids() {
        return bids;
    }

    public void setBids(List<Bid> bids) {
        this.bids = bids;
    }   
}
Run Code Online (Sandbox Code Playgroud)
@Entity
@Table(name="BIDS")
public class Bid implements Serializable{
    private static final long serialVersionUID = 1L;

    ...   
    private Item item;    
    ...

    @Id
    @Column(name="BID_ID")
    public Long getBidId() {
        return bidId;
    }

    public void setBidId(Long bidId) {
        this.bidId = bidId;
    }

    @ManyToOne
    @JoinColumn(name="BID_ITEM_ID",referencedColumnName="ITEM_ID")
    public Item getItem() {
        return item;
    }

    public void setItem(Item item) {
        this.item = item;
    }    
    ...        
}
Run Code Online (Sandbox Code Playgroud)

现在提取项目时

@Override
public List<Bid> getBidsForItem(long itemId) {
    Item item = em.find(Item.class, itemId); // em -> Entity manager
    return item.getBids();
}
Run Code Online (Sandbox Code Playgroud)

所述item.getBids()返回一个空列表(大小= 0,不为空).为了获得给定项目的出价,应该做哪些更改?

编辑:
按照注释中的建议启用查询日志记录

<property name="eclipselink.logging.level.sql" value="FINE"/>
<property name="eclipselink.logging.parameters" value="true"/>
Run Code Online (Sandbox Code Playgroud)

我注意到为插入语句列出了查询但是没有列出对应的查询em.find(Item.class, itemId).

编辑2(ANSWER):
这个问题是我addBids()无状态bean的功能,这让我传递一个项目的对象.这意味着Item对象永远不会处于持久化上下文中.正确的方法是

  1. 传递itemId
  2. 使用实体管理器find()方法查找Item实体.这可确保Item对象处于持久化上下文中.
  3. 将出价对象添加到要出价的项目和项目
  4. 在Bid上调用实体管理器persist().

更正了addBids()方法:

public Bid addBids(Date bidDate, Double bidPrice, long itemId, String bidder) {  
        Item item = em.find(Item.class, itemId);  
        Bid bid = new Bid(bidDate, bidPrice, item, bidder);  
        item.getBids().add(bid);  
        em.persist(bid);  
        return bid;  
}  
Run Code Online (Sandbox Code Playgroud)

感谢@Chris指出.

Kev*_*sox 1

尝试实例化 aArrayList<Bid>并将其分配给List<Bid>声明。

  @OneToMany(mappedBy="item")
  protected List<Bid> bids = new ArrayList<Bid>();
Run Code Online (Sandbox Code Playgroud)