当前位置: 首页 > 知识库问答 >
问题:

将@IDClass与Hibernate和arquillian force CascadeType.insert一起用于实体复合主键的ManyToOne外键对象

慕胡媚
2023-03-14
@Entity
@Table(name = "ORDERS")
public class Orders extends BaseEntity {

    private static final long serialVersionUID = 1L;

    @Id
    @Column(name = "ORDERNO")
    @GeneratedValue(strategy = GenerationType.AUTO)
    private Long orderNo ;

    @OneToMany(cascade = CascadeType.ALL, mappedBy = "order", fetch = FetchType.LAZY)
    private List<OrderDetail> orderDetailsList ;

    // setters and getters
}
@Entity
@Table(name = "ORDERDETAILS")
@IdClass(OrderDetailsPK.class)
public class OrderDetail extends BaseEntity {

private static final long serialVersionUID = 1L;

@Id
@JoinColumn(name = "ORDERNO", referencedColumnName = "ORDERNO")
@ManyToOne(optional = false, fetch = FetchType.LAZY)
private Orders order;

@Id
@JoinColumn( name = "ITEMNO", referencedColumnName = "ITEMNO", insertable = false, updatable = false)
@ManyToOne(cascade = CascadeType.REFRESH,optional = false, fetch = FetchType.LAZY)
//@Cascade({CascadeType.DETACH}) // I tried this but did not work, it keep try to insert the item.
private Item item;

@Id
@Column(name = "LINETYPE")
private String lineType;

@Id
@Column(name = "PROMITEMNO")
private String promItemNo;
@Entity
@Table(name = "ITEM")
public class Item extends BaseEntity {

    private static final long serialVersionUID = 1L;

    @Id
    @Column(name = "ITEMNO")
    private String itemno;
    // setters and getters

   @Override
   public int hashCode() {
    int hash = 0;
    hash += (itemno != null ? itemno.hashCode() : 0);
    return hash;
   }

   @Override
   public boolean equals(Object object) {
    if (!(object instanceof Item)) {
        return false;
    }
    Item other = (Item) object;
    System.out.println("Item Equal Method = " + !((this.itemno == null &&        other.itemno != null) || (this.itemno != null && !this.itemno.equals(other.itemno))));
    return !((this.itemno == null && other.itemno != null) || (this.itemno != null && !this.itemno.equals(other.itemno)));
}

  @Override
  public String toString() {
    return "com.unilever.sas.model.entities.masterdata.Item[ itemno=" + itemno + " ]";
}

}

OrderDetailSPK

public class OrderDetailsPK  implements Serializable 
{

    private static final long serialVersionUID = 1L;

    private Long order;
    private String item;
    private String lineType;
    private String promItemNo;

    public OrderDetailsPK() {
    }

    public OrderDetailsPK(Long order, String item, String lineType, String promItemNo) {
        this.order = order;
        this.item = item;
        this.lineType = lineType;
        this.promItemNo = promItemNo;
    }

    public Long getOrder() {
        return order;
    }

    public String getItem() {
        return item;
    }

    public String getLineType() {
        return lineType;
    }


    public String getPromItemNo() {
        return promItemNo;
    }

    @Override
    public int hashCode() {
        int hash = 5;
        hash = 73 * hash + Objects.hashCode(this.order);
        hash = 73 * hash + Objects.hashCode(this.item);
        hash = 73 * hash + Objects.hashCode(this.lineType);
        hash = 73 * hash + Objects.hashCode(this.promItemNo);
        return hash;
    }

    @Override
    public boolean equals(Object obj) {
        if (this == obj) {
            return true;
        }
        if (obj == null) {
            return false;
        }
        if (getClass() != obj.getClass()) {
            return false;
        }
        final OrderDetailsPK other = (OrderDetailsPK) obj;
        if (!Objects.equals(this.item, other.item)) {
            return false;
        }
        if (!Objects.equals(this.lineType, other.lineType)) {
            return false;
        }
        if (!Objects.equals(this.promItemNo, other.promItemNo)) {
            return false;
        }
        if (!Objects.equals(this.order, other.order)) {
            return false;
        }
        return true;
    }

    @Override
    public String toString() {
        return "OrderDetailsPK{" + "order=" + order + ", item=" + item + ", lineType=" + lineType + ", promItemNo=" + promItemNo + '}';
    }

阿奎利安试验

@RunWith(Arquillian.class)
public class OrdersFacadeTest
{


@Inject
OrdersFacadeLocal ordersFacade ;

@Inject    
ItemFacadeLocal itemFacade ;

@Test
public void testCreateOrder() throws Exception 
{
    Item item = itemFacade.find("20247912");
    Orders order = new Orders();

    OrderDetail orderDetail = new OrderDetail();
    orderDetail.setOrder(order);
    orderDetail.setItem(item);
    orderDetail.setLineType("NLI");
    orderDetail.setPromItemNo("99999");

    List<OrderDetail> orderDeialsList = new ArrayList<>();
    orderDeialsList.add(orderDetail);

    order.setOrderDetailsList(orderDeialsList);      

    ordersFacade.create(order);

    Orders createdOrder = ordersFacade.find(order.getOrderNo());
    assertEquals(order, createdOrder);
}

共有1个答案

锺英彦
2023-03-14

这可能是一个bug,但这里也有一些奇怪的映射选择。

为什么@joincolumn不允许在插入或更新时设置FK?在这种情况下谁应该设置FK?

@JoinColumn( 
    name = "ITEMNO", 
    referencedColumnName = "ITEMNO", 
    insertable = false, updatable = false
)

如果您可以用测试用例复制它,那么您应该打开一个Jira问题。

 类似资料:
  • 花了3天时间寻找解决方案,最后我来到这里寻求社区智慧。 我有如下的自我引用实体: 我通过手动运行它来确保请求不会返回数据库中的任何内容,但发现如果我将更改为,它将返回数据,因此,块中可能存在错误

  • 我正在尝试使用hibernate解决应用程序中的数据库映射问题。我们使用JPA注释这些类,到目前为止我们是成功的。但是,我们现在想引入一个组合键,它包含一个标识客户的唯一字符串和一个标识数据库条目的字符串。为了设置复合键,我们使用一个名为MandtId.java的IdClass。 然而,我们的映射似乎不起作用,因为它在另一侧找不到要连接的列。 以下是一些代码片段来显示我们的注释: MandtId.

  • 我有一个实体,它的复合主键由两个字段组成,其中一个也是复合外键的一部分。 背景:我有实体<代码>人员 、<代码>区域 和<代码>会话 。 与具有多对多关系,使用称为“和实体。 所以,我有,主键为(,)。本身是的外键。 也有一个字段。我希望(,)是的复合外键。 我的PersonSession代码: } 这看起来不错,它在数据库中创建了所有正确的关系。当我尝试插入个性化会话对象时,问题就出现了——ar

  • 我有一些实体: 当我试图保存新的cbonus记录时,出现异常: org.postgresql.util.PSQLException: ERROR: null值在列"bank_id"的关系"cBonus"违反了非空约束详细信息:失败的行包含(773, gp3, null, null, f)。 和查询 DEBUG 24817-[nio-8080-exec-4]org . hibernate . SQL

  • 问题内容: 我有一个类似的问题,如下所示,但解决方案无法解决我的问题。 休眠复合主键包含复合外键,如何映射 我正在尝试加入2个表,每个表都有一个带有部分外键引用的复合主键。 在一个: 在BPK中: 上面的方法给我这个异常: 你能帮忙吗? 问题答案: 假设f1和F2唯一标识A并存在于APK中,则可以通过几种方式使用JPA 2.0的派生ID。最容易显示的是: 这里的关键点是B对A的引用控制了外键字段f

  • 问题内容: 我有一个类似的问题,如下所示,但解决方案无法解决我的问题。 休眠复合主键包含复合外键,如何映射 我正在尝试加入2个表,每个表都有一个带有部分外键引用的复合主键。 在一个: 在BPK中: 上面的方法给我这个异常: 你能帮忙吗? 问题答案: 假设f1和F2唯一标识A并存在于APK中,则可以通过几种方式使用JPA 2.0的派生ID。最容易显示的是: 这里的关键点是B对A的引用控制了外键字段f