Hibernate oneToMany 抽象类覆盖 ID

标签 hibernate

我正在使用 JPA 1.0,所以我能做的事情受到限制,但我仍然认为应该可以执行以下操作,但我无法让它工作......

Table CustomerA
    a_id

Table ProductB
    a_id
    b_id

Table ProductC
    a_id
    c_id

@Entity
@Inheritance(strategy=InheritanceType.TABLE_PER_CLASS)
public abstract class AbstractProduct {

    @Id
    @GeneratedValue....
    private Long id;

    private String name;

 @ManyToOne()
 JoinColumn(name="a_id")
 private CustomerA customerA;

}

现在我想创建一个子类,它可以覆盖Id或基于Table APK创建一个复合Key,并且派生表的键...

@Entity
@Table(name="ProductB") 
public class ProductB extends AbstractProduct {

     //@AttributeOverride(name="id", column=@Column(name="B_ID") //Can only be used     with MappedSuperClass and also Emmbedded Objects
     //@Id //cant override the ID Column so that cant go here
    //PrimaryKeycolumn join not what i want here
    private Long productB_id;

    private String productName;
}

@Entity
@Table(name="CustomerA") 
public class CustomerA
{
    @Id
    @GeneratedValue....
    @Column(name="a_id")
    private Long aId

     @OneToMany(mappedBy="customerA", cascade=CascadeType.ALL)
    private Set<AbstractProduct> product;
} 

因此本质上CustomerA可以包含许多产品,但它始终只能是ProductBProductC。我如何覆盖子类中的Id,因为您不能使用attributeoverride和Entity,并且如果您使用@Entity,则必须指定每当您指定@Entity时,@Id。我已经阅读了 jpa wiki,它看起来相当复杂并且很难在 JPA 1.0 中实现这一点,但我想知道我是否遗漏了一些东西?

最佳答案

我的建议是在两个产品之间共享一个基类,以便您可以以单一方式引用它们。在 JPA/Hibernate 中,这意味着创建一个共享表,其中将包含产品的公共(public)元素,即对 CustomerA 的引用。

实现这一点的方法是使用“JOINED”继承策略:

@Inheritance(strategy=InheritanceType.JOINED)

使用此策略的缺点是它可能与 AbstractProduct 基类中已使用的现有“TABLE_PER_CLASS”策略发生冲突......尽管这可能是用于此目的的适当基类。据我所知,你不能混合继承策略。

这是一个例子:

@Entity
@Table(name="CustomerA") 
public class CustomerA
{
    @Id
    @GeneratedValue....
    @Column(name="a_id")
    private Long aId

    @OneToMany(mappedBy="customerA", cascade=CascadeType.ALL)
    private Set<AbstractProduct> product;
} 

@Entity
@Table(name="ProductB") 
public class ProductB extends AbstractProduct {

    private String specificProductBValue;
}

@Entity
@Table(name="ProductC") 
public class ProductC extends AbstractProduct {

    private String specificProductCValue;
}

@Entity
@Inheritance(strategy=InheritanceType.JOINED)
public abstract class AbstractProduct {

    @Id
    @GeneratedValue....
    private Long id;

    private String name;

    @ManyToOne()
    JoinColumn(name="customer_id")
    private CustomerA customerA;

}

看起来您的示例已经差不多完成了,只需要使用正确的继承策略即可。

此外,这假设您没有其他产品扩展您的 AbstractProduct 基类。如果您这样做并且不希望客户引用这些内容,那么您将必须重新考虑您的域设计。

希望有帮助。

关于Hibernate oneToMany 抽象类覆盖 ID,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8233447/

相关文章:

java - 如何加载实际的 Hibernate 实体关联而不是 LAZY 代理

hibernate - 来自 grails 的带有 javaDB 和 Hibernate 的用户表

java - Hibernate 生成的额外 sql

java - hibernate 映射中的 2 级继承问题

java - 如何在 postgres 中没有时区的情况下节省时间。我正在使用 hibernate Spring MVC

java - Spring JPA Join效率——每次迭代创建查询

java - 如何覆盖继承类上的 hibernate JPA 过滤器?

hibernate - java.lang.VerifyError : class net. sf.cglib.core.DebuggingClassWriter

java - 使用 SessionFactory bean 的 setter 注入(inject)时出现 NullPointerException

java - 使用 Hibernate/JPA 根据具体情况从 @Embedded 属性中排除字段