Hi,
I'd like to illustrate my problem with an example: I have two entities Item and Category. They are connected with a many to one relationship, i.e. a category may contain multiple items and one item is in one category. Item has an id and the foreign key as a composite key. In SQL it's something like this (it's Postgres but this shouldn't matter):
Code:
create table category ( id serial, name varchar, primary key (id));
create table item ( id serial, cat_id bigint, name varchar, primary key (id, cat_id), foreign key (cat_id) references category(id));
creating the following tables:
Code:
Table "public.category"
Column | Type | Modifiers
--------+------------------------+-------------------------------------------------------
id | bigint | not null default nextval('category_id_seq'::regclass)
name | character varying(255) |
Indexes:
"category_pkey" PRIMARY KEY, btree (id)
Table "public.item"
Column | Type | Modifiers
--------+-------------------+---------------------------------------------------
id | integer | not null default nextval('item_id_seq'::regclass)
cat_id | bigint | not null
name | character varying |
Indexes:
"item_pkey" PRIMARY KEY, btree (id, cat_id)
Foreign-key constraints:
"item_cat_id_fkey" FOREIGN KEY (cat_id) REFERENCES category(id)
I don't know how to do this with Hibernate using only JPA annotations.
My classes are as follows (I left out getters/setters and the like):
Code:
@Entity
public class Category {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private long id;
@Column
private String name;
}
Code:
@Entity
@IdClass(Item.PK.class)
public class Item {
@Id
@GeneratedValue(strategy = GenerationType.IDENTITY)
private long id;
@Id
@Column(name = "cat_id", updatable = false, insertable = false)
private long categoryId;
@ManyToOne
@JoinColumn(name = "cat_id")
private Category category;
@Column
private String name;
public static class PK implements Serializable {
private long id;
private long categoryId;
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public long getCategoryId() {
return categoryId;
}
public void setCategoryId(long categoryId) {
this.categoryId = categoryId;
}
}
}
When I run Hibernate in DDL mode it behaves rather strange. The category table gets created like this:
Code:
Table "public.item"
Column | Type | Modifiers
------------+------------------------+-----------
categoryid | bigint | not null
id | bigint | not null
name | character varying(255) |
cat_id | bigint |
Indexes:
"item_pkey" PRIMARY KEY, btree (categoryid, id)
Foreign-key constraints:
"fk22ef33be7f7067" FOREIGN KEY (cat_id) REFERENCES category(id)
So I get another column categoryid which is used as a primary key but not the foreign key. In EclipseLink this works fine.
The thing is I try to migrate an existing DAL using JDBC to JPA and I can't really mess with the tables. I also can't create the table by hand because all INSERT statements rely on the categoryid column. When I persist items the categoryid always gets bound to 0 (zero) so it really serves no purpose.
I tried different combinations of updatable/insertable and @Column, @JoinColumn, @PrimaryKeyJoinColumn to no avail. Maybe I don't see the wood for the trees. As I said it works in EclipseLink but I'd really love to be independent of the implementation and I'd hate to lose that because of such a simple mapping issue.
I hope you can give me some hints where my mistake is.
Thank you
mK