我正在尝试将JPA @Embeddable
与Hibernate一起使用。实体和embeddable都有一个名为id
的属性:
@MappedSuperclass
public abstract class A {
@Id
@GeneratedValue
long id;
}
@Embeddable
public class B extends A {
}
@Entity
public class C extends A {
B b;
}
这会引发org.hibernate.MappingException: component property not found: id
。
我想避免使用@AttributeOverrides
。因此我尝试设置spring.jpa.hibernate.naming_strategy=org.hibernate.cfg.DefaultComponentSafeNamingStrategy
(我正在使用Spring Boot)。这没有任何影响(同样的例外)。但是,我怀疑该设置被忽略了,因为指定一个不存在的类不会引发异常。
奇怪的是,即使有了这个变种
@Entity
public class C extends A {
@Embedded
@AttributeOverrides( {
@AttributeOverride(name="id", column = @Column(name="b_id") ),
} )
B b;
}
我仍然得到同样的错误。
答案 0 :(得分:2)
命名策略配置已更改。根据{{3}}的新方法是:
spring.jpa.hibernate.naming.implicit-strategy=org.hibernate.boot.model.naming.ImplicitNamingStrategyComponentPathImpl
此外,您不得在@Id
内使用@Embeddable
。因此,我为embeddables创建了一个单独的@MappedSuperclass
:
@MappedSuperclass
public abstract class A {
@Id
@GeneratedValue
long id;
}
@MappedSuperclass
public abstract class E {
@GeneratedValue
long id;
}
@Embeddable
public class B extends E {
}
@Entity
public class C extends A {
B b;
}
这样,表格C
有两列id
和b_id
。缺点当然是A
和E
引入了一些冗余。关于DRY方法的评论非常受欢迎。