使用复合主键将值存储在连接表中

问题描述 投票:0回答:1

我有桌子

Offer
Area
,因为一个报价可以有多个区域,我也有
OfferArea

Offer{
   id  bigserial,
   client_id  bigserial,
   text varchar(500)
} 


Area{
   id bigserial,
   name varchar(50)
}

offer_area{
   offer_id bigserial // pk
   area_id  bigserial // pk
}

如您所见,

OfferArea
具有复合主键。

我正在使用JPA:

@Embeddable
@Getter
@Setter
public class OfferAreaPk implements Serializable {
    private long offerId;
    private long areaId;
}



@Entity
@Table(name = "offer_area")
@Getter
@Setter
public class OfferAreaEntity {
    @EmbeddedId
    private OfferAreaPk offerAreaPk;

    @ManyToOne
    @MapsId("offerId")
    private OfferEntity offer;

    @ManyToOne
    @MapsId("areaId")
    private AreaEntity area;
}

现在在我的 Offer 实体中我有这个:

@OneToMany(mappedBy = "offer")
private List<OfferAreaEntity> locations;

在区域实体中我有这个:

@OneToMany(mappedBy = "area")
private List<OfferAreaEntity> specializations;

但是我如何将其保存到数据库?

如果我这样做:

 OfferEntity offerEntity= offerRepository.save(offerEntity);
AreaEntity areaEntity = areaEntityRepository.findById(areaId);
OfferAreaEntity offerAreaEntity = new OfferAreaEntity();
offerAreaEntity.setOffer(offerEntity);
offerAreaEntity.setArea(areaEntity );
offerAreaRepository.save(offerAreaEntity)

我收到错误:

"org.springframework.orm.jpa.JpaSystemException: Could not set value of type [java.lang.Long]: 'OfferAreaPk.areaId' (setter)"
 

如果我尝试将其另存为:

OfferEntity offerEntity = new OfferEntity();
AreaEntity areaEntity = areaEntityRepository.findById(areaId);
// other attributes
 OfferAreaEntity offerAreaEntity = new OfferAreaEntity();
 offerAreaEntity.setOffer(offerEntity);
 offerAreaEntity.setArea(areaEntity );
offerEntity.setLocations(Arrays.asList(offerAreaEntity));
offerRepository.save(offerEntity);

OfferArea 选项卡中未保存任何内容。

如何保存数据?感谢您的帮助!

spring spring-boot jpa spring-data-jpa
1个回答
0
投票

不需要在加入表中填写以下内容,因为表中的优惠和区域 ID 已经是唯一的。

@EmbeddedId
private OfferAreaPk offerAreaPk;

因此尝试 (cascade = CascadeType.ALL) 以及所有映射注释。

@Entity
@Table(name = "offer_area")
@Getter
@Setter
public class OfferAreaEntity {
    
    @ManyToOne(cascade = CascadeType.ALL)    
    @MapsId("offerId")
    private OfferEntity offer;

    @ManyToOne(cascade = CascadeType.ALL)    
    @MapsId("areaId")
    private AreaEntity area;
}

jpa 级联类型

© www.soinside.com 2019 - 2024. All rights reserved.