JPA composite primary key [duplicate]
I have the following classes in my JPA model (getters, setters, and irrelevant fields omitted):
@Entity @Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public class Currency {
@Id
private Integer ix;
}
@Entity @Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public class Product {
@Id @GeneratedValue(strategy = GenerationType.IDENTITY)
private Integer id;
}
I need to define a class Price
, such that when the DDL is generated from the classes, the primary key of the corresponding table is composed of the keys for Product
and Currency
. I've tried the following:
@Entity @Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
@IdClass(PricePK.class)
public class Price {
@Id @ManyToOne(optional = false)
private Product product;
@Id
@ManyToOne(optional = false)
private Currency currency;
}
@Embeddable
public class PricePK implements Serializable {
Integer product;
Integer currency;
}
But this generates the following for the PRICE
table:
create table PRICE (
currency_id int null,
product_id int null,
primary key (currency_id, product_id)
);
Notice that both currency_id
and product_id
are nullable, which causes the following error when I try to load the DDL into SQL Server
Cannot define PRIMARY KEY constraint on nullable column in table 'PRICE'
I don't understand why these are nullable, because in the domain model they are annotated
@ManyToOne(optional = false)
The DDL is generated using the org.hibernate.dialect.SQLServerDialec开发者_C百科t
SQL dialect.
Recently I created ManyToMany relation using Composite Primary key and annotation as bi directional @OneToMany
. This code works flawless. Maybe it will help:
Mapping ManyToMany with composite Primary key and Annotation:
Since you are using @IdClass
, the PricePK
class need not be marked with the @Embeddable
annotation. An example is given in http://www.java2s.com/Code/Java/JPA/SetIdClassforCompoundKey.htm
I tried your code removing the @Embeddable
on PricePK
class, and the price table generated in MYSQL database with not null fields.
Following is how you could use @EmbeddedId
to achieve the required result:
(getters and setters omitted)
@Entity
@Inheritance(strategy = InheritanceType.TABLE_PER_CLASS)
public class Price {
@EmbeddedId
PricePK pricePk;
}
@Embeddable
public class PricePK implements Serializable {
@ManyToOne(optional = false)
private Product product;
@ManyToOne(optional = false)
private Currency currency;
}
精彩评论