我在示例应用程序中有两个Entity类:
@Entity
public class Person {
...
@OneToMany(mappedBy = "owner", cascade= CascadeType.ALL)
@MapKeyColumn(name="phone_type")
private Map<String, Phone> phones = new HashMap<String, Phone>();
public Map<String, Phone> getPhones() {
return phones;
}
public void setPhones(Map<String, Phone> phones) {
this.phones = phones;
}
...
}
@Entity
public class Phone {
...
@ManyToOne
private Person owner;
public Person getOwner() {
return owner;
}
public void setOwner(Person owner) {
this.owner = owner;
}
...
}
即使我没有在Phone对象中包含phone_type字段,我希望它根据Person类HashMap中的值保存在DB中。 我没有将字段添加到Phone对象中以避免冗余地管理数据 - 因为phone_type已经作为地图中的键出现。
当我尝试持久化Person对象时,我看到hibernate运行不包括phone_type列的插入 - 例如:
insert into person (first_name, last_name, id) values (?, ?, ?)
insert into phone (number, owner_id, id) values (?, ?, ?)
我错过了一些可以工作的东西吗?据我所知,我的例子复制了一个:https://en.wikibooks.org/wiki/Java_Persistence/Relationships#Map_Key_Columns_.28JPA_2.0.29,但我无法真正开始工作。
感谢您的帮助!
答案 0 :(得分:0)
编辑:嗯,我最初通过删除MapKeyColumn(name="phone_type")
注释来实现它。有了它,它如上所述表现得很奇怪。我将mappedBy="owner"
重新放入,并且phones_KEY(默认情况下名为phones_KEY,没有MapKeyColumn
注释)现在位于Phone
表中。
create table Phone (id bigint not null, name varchar(255), owner_id bigint, phones_KEY varchar(255), primary key (id))
当我进行插入时,它首先执行两次插入,没有phones_KEY,然后是phones_KEY字段的更新,可能是在一次交易中。
insert into Person (name, id) values (?, ?)
insert into Phone (name, owner_id, id) values (?, ?, ?)
update Phone set phones_KEY=? where id=?
在我看来,它(hibernate 4.3)在将phones_KEY
字段命名为phone_type
时不应该有问题,但我想它确实存在问题。我不知道该告诉你什么。
更新:我尝试了这个,它解决了上述无法命名phone_type
列的问题。我不知道您的表格结构,但这会生成与上面的注释相同的表格结构,这会将phone_Key
列放在Phone
实体中。
@Entity
public class Person {
...
@OneToMany( mappedBy="owner", fetch=FetchType.EAGER, cascade=CascadeType.ALL)
private List<Phone> phones;
...
}
和
@Entity
public class Phone {
...
@ManyToOne
private Person owner;
private String phone_type;
...
}
您会注意到即使Entities
不同,创建的表结构也是相同的。在这种情况下,不是将phone_type
作为Map
密钥,而是使用MapKeyColumn
声明名称,而是将其作为名为{{1的字段放在Phone
实体中}}。使用OneToMany phone_type
代替地图。由于关系是由List
专门映射的,因此Map或List都不会影响映射。现在,插入显示owner
表中的phone_type
插入。
Phone
希望这有帮助。