如何处理 jpa/hibernate 的共享列?

How to handle shared column with jpa/hibernate?

我正在将 money/currency 存储在我想使用 JPA/Hibernate 映射的数据库中,但是同一实体上的两个不同映射需要一列。

数据库架构:

id: number
currency_code: string
total: number
sub_total: number

POJO:

public class MyEntity {
    private long id;
    private Money total;
    private Money subTotal;
}

public class Money {
    private  CurrencyCode currencyCode;
    private  BigInteger value;
}

我用 JPA/Hibernate 遇到的问题是 currency_code 需要同时映射到 totalsubTotal:

@Entity
@Table(name = "MyTable")
public class MyEntity {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id")
    private long id;

    @Type(type = "customMoneyType")
    @Columns(columns = {
            @Column(name = "currency_code"),
            @Column(name = "total"),
    })
    private Money total;

    @Type(type = "customMoneyType")
    @Columns(columns = {
            @Column(name = "currency_code"),
            @Column(name = "sub_total"),
    })
    private Money subTotal;
}

这导致 Caused by: org.hibernate.MappingException: Repeated column in mapping for entity

这两个字段都需要可更新且可为空。列的共享是遗留的,但在不久的将来不会改变。话虽如此,我对不太理想的解决方案持开放态度,这些解决方案在可以更改数据库架构之前仍然有效。

只需使 MyEntity 与 table 完全对齐。将 currencyCodetotalsubTotal 字段保留为 class 的内部字段,并使用 OOP 封装技术公开客户端通过 Money 与它们一起工作的方法值对象。像 :

@Entity
@Table(name = "entity")
public class MyEntity {

    @Id
    @Column(name = "id")
    private long id;

    @Column(name = "currency_code")
    private CurrencyCode currenyCode;
    
    @Column(name = "total")
    private BigInteger total;

    @Column(name = "sub_total")
    private BigInteger subTotal;


    public Money getTotal(){
      return new Money(currenyCode, total);
    }

    public Money getSubTotal(){
      return new Money(currenyCode, subTotal);
    }

    public void updateTotal(Money m){
        this.currencyCode = m.getCurrenyCode();
        this.total = m.getValue();
    }

    public void updateSubTotal(Money m){
        this.currencyCode = m.getCurrenyCode();
        this.subTotal = m.getValue();
    }

}