如何使用 JPA 和 Hibernate 映射组合键?
在这段代码中,如何为复合键生成一个Java类(how to composite key in hibernate):
create table Time (
levelStation int(15) not null,
src varchar(100) not null,
dst varchar(100) not null,
distance int(15) not null,
price int(15) not null,
confPathID int(15) not null,
constraint ConfPath_fk foreign key(confPathID) references ConfPath(confPathID),
primary key (levelStation, confPathID)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
In this code, how to generate a Java class for the composite key (how to composite key in hibernate):
create table Time (
levelStation int(15) not null,
src varchar(100) not null,
dst varchar(100) not null,
distance int(15) not null,
price int(15) not null,
confPathID int(15) not null,
constraint ConfPath_fk foreign key(confPathID) references ConfPath(confPathID),
primary key (levelStation, confPathID)
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(8)
要映射复合键,您可以使用
EmbeddedId
或IdClass
注释。我知道这个问题并不严格涉及 JPA,但规范定义的规则也适用。所以他们在这里:使用
IdClass
复合主键的类可能如下所示(可以是静态内部类):
实体:
IdClass
注释将多个字段映射到表 PK 。使用
EmbeddedId
复合主键的类可能如下所示(可以是静态内部类):
实体:
@EmbeddedId
注释将 PK 类映射到表 PK 。差异:
@EmbeddedId
以某种方式更清楚地传达了该密钥是一个复合密钥,并且当组合的pk是一个有意义的实体时,IMO是有意义的本身或在您的代码中重用。@IdClass
用于指定某些字段组合是唯一的,但这些字段没有特殊含义。它们还会影响您编写查询的方式(使查询或多或少变得冗长):
with
IdClass
与
EmbeddedId
参考
To map a composite key, you can use the
EmbeddedId
or theIdClass
annotations. I know this question is not strictly about JPA but the rules defined by the specification also applies. So here they are:With an
IdClass
The class for the composite primary key could look like (could be a static inner class):
And the entity:
The
IdClass
annotation maps multiple fields to the table PK.With
EmbeddedId
The class for the composite primary key could look like (could be a static inner class):
And the entity:
The
@EmbeddedId
annotation maps a PK class to table PK.Differences:
@EmbeddedId
somehow communicates more clearly that the key is a composite key and IMO makes sense when the combined pk is either a meaningful entity itself or it reused in your code.@IdClass
is useful to specify that some combination of fields is unique but these do not have a special meaning.They also affect the way you write queries (making them more or less verbose):
with
IdClass
with
EmbeddedId
References
您需要使用
@EmbeddedId
:You need to use
@EmbeddedId
:假设您有以下数据库表:
首先,您需要创建
@Embeddable
持有复合标识符:有了这个,我们可以通过使用
@EmbeddedId
注释来映射使用复合标识符的Employee
实体:Phone
与Employee
具有@ManyToOne
关联的实体,需要通过两个@JoinColumn
映射从父类引用复合标识符:Assuming you have the following database tables:
First, you need to create the
@Embeddable
holding the composite identifier:With this in place, we can map the
Employee
entity which uses the composite identifier by annotating it with@EmbeddedId
:The
Phone
entity which has a@ManyToOne
association toEmployee
, needs to reference the composite identifier from the parent class via two@JoinColumn
mappings:主键类必须定义 equals 和 hashCode 方法
从技术上讲:您应该遵循 Liskows 替换原则并忽略对称性。
http://www.laliluna.de/jpa-hibernate-guide/ch06s06.html
The primary key class must define equals and hashCode methods
More technically: You should follow the Liskows Substitution Principle and ignore symmetricity.
http://www.laliluna.de/jpa-hibernate-guide/ch06s06.html
看来你是从头开始做这件事。尝试使用可用的逆向工程工具,例如数据库中的 Netbeans 实体,至少可以实现基础知识的自动化(例如嵌入式 id)。如果您有很多表,这可能会变得非常令人头痛。我建议避免重新发明轮子,并使用尽可能多的可用工具将编码减少到最少和最重要的部分,即您打算做的事情。
Looks like you are doing this from scratch. Try using available reverse engineering tools like Netbeans Entities from Database to at least get the basics automated (like embedded ids). This can become a huge headache if you have many tables. I suggest avoid reinventing the wheel and use as many tools available as possible to reduce coding to the minimum and most important part, what you intent to do.
让我们举一个简单的例子。假设有两个名为
test
和customer
的表,描述如下:还有一个表用于跟踪
test
和customer
:我们可以看到表
tests_purchased
中的主键是复合键,所以我们将使用...
标记。因此hbm.xml
映射文件中的PurchasedTest.hbm.xml
将如下所示:但它并没有在这里结束。在 Hibernate 中,我们使用 session.load (
entityClass
,id_type_object
) 来使用主键查找并加载实体。在复合键的情况下,ID 对象应该是一个单独的 ID 类(在上面的例子中是一个PurchasedTestId
类)它只声明如下的主键属性:重要的一点是我们还实现了两个函数
hashCode()
和equals()
,因为 Hibernate 依赖于它们。Let's take a simple example. Let's say two tables named
test
andcustomer
are there described as:One more table is there which keeps the track of
test
s andcustomer
:We can see that in the table
tests_purchased
the primary key is a composite key, so we will use the<composite-id ...>...</composite-id>
tag in thehbm.xml
mapping file. So thePurchasedTest.hbm.xml
will look like:But it doesn't end here. In Hibernate we use session.load (
entityClass
,id_type_object
) to find and load the entity using primary key. In case of composite keys, the ID object should be a separate ID class (in above case aPurchasedTestId
class) which just declares the primary key attributes like below:Important point is that we also implement the two functions
hashCode()
andequals()
as Hibernate relies on them.复合键类
实体类
Composite Key Class
Entity Class
另一种选择是将其映射为 ConfPath 表中复合元素的映射。
不过,此映射将受益于 (ConfPathID,levelStation) 上的索引。
映射:
Another option is to map is as a Map of composite elements in the ConfPath table.
This mapping would benefit from an index on (ConfPathID,levelStation) though.
Mapping: