gpt4 book ai didi

java - Hibernate - 具有附加列的链接表 - 保存在一个事务中

转载 作者:行者123 更新时间:2023-11-30 05:10:31 25 4
gpt4 key购买 nike

我正在学习Hibernate,刚刚阅读了《Java Persistance with Hibernate》一书的“7.2.3 添加列来连接表”一章。我的目标是在一次事务中保存 Item、Category 和 CategorizedItem。

那里有一个构造函数(第305页):

public CategorizedItem(String username, Category category, Item item) {
// Set fields
this.username = username;

this.category = category;
this.item = item;

// Set identifier values
this.id.categoryId = category.getId();
this.id.itemId = item.getId();

// Guarantee referential integrity
category.getCategorizedItems().add(this);
item.getCategorizedItems().add(this);
}

它接受类别和项目对象。如果我创建一个类别和一个项目并希望使用此技术将它们连接起来,那么显然必须在之前保留它们,因为category.getId() 和 item.getId() 返回 null。

是否有“Hibernate包中的技巧”可以级联保存连接表?连接表有附加列。我想将所有三个对象保存在网页 Controller 的 onSuccess 处理程序中。必须插入所有三个实体或都不插入任何实体。

最佳答案

你说

My goal is to save Item, Category and CategorizedItem in one transaction

Hibernate包里有没有一个技巧可以级联保存连接表?

是的,使用 MutableInt

@Entity
public class CategorizedItem implements Serializable {

private CategorizedItemId categorizedItemId;

private String userName;

private Category category;
private Item item;

/**
* required no-arg constructor
*/
public CategorizedItem() {}
public CategorizedItem(CategorizedItemId categorizedItemId) {
this.categorizedItemId = categorizedItemId;
}
public CategorizedItem(String userName, Category category, Item item) {
this.userName = userName;

this.categorizedItemId = new CategorizedItemId(category.getIdAsMutableInt(), item.getIdAsMutableInt());
}

@EmbeddedId
public CategorizedItemId getCategorizedItemId() {
return this.categorizedItemId;
}

@ManyToOne(fetch=FetchType.LAZY)
@JoinColumn(name="CATEGORY_ID", insertable=false, updateable=false)
public Category getCategory() {
return this.category;
}

@ManyToOne(fetch=FetchType.LAZY)
@JoinColumn(name="ITEM_ID", insertable=false, updateable=false)
public Item getItem() {
return this.item;
}

// setter's goes here

/**
* It MUST implements Serializable
* It MUST overrides equals and hashCode method
* It MUST has a no-arg constructor
*
* Hibernate/JPA 1.0 does not support automatic generation of compound primary key
* You SHOULD set up manually
*/
@Embeddable
public static class CategorizedItemId implements Serializable {

private MutableInt categoryId = new MutableInt(-1);
private MutableInt itemId = new MutableInt(-1);

/**
* required no-arg constructor
*/
public CategorizedItemId() {}
public CategorizedItemId(MutableInt categoryId, MutableInt itemId) {
this.categoryId = categoryId;
this.itemId = itemId;
}

@Column(name="CATEGORY_ID", updateable=false, nullable=false)
public Integer getCategoryId() {
return this.categoryId.intValue();
}

public void setCategoryId(Integer categoryId) {
return this.categoryId.setValue(categoryId);
}

@Column(name="ITEM_ID", updateable=false, nullable=false)
public Integer getItemId() {
return this.itemId.intValue();
}

public void setItemId(Integer itemId) {
return this.itemId.setValue(itemId);
}

// getter's and setter's

@Override
public boolean equals(Object o) {
if(!(o instanceof CategorizedItemId))
return null;

finalCategorizedItemId other = (CategorizedItemId) o;
return new EqualsBuilder().append(getCategoryId(), other.getCategoryId())
.append(getItemId(), other.getItemId())
.isEquals();
}

@Override
public int hashCode() {
return new HashCodeBuilder().append(getCategoryId())
.append(getItemId())
.toHashCode();
}

}

}

这里是类别

@Entity
public class Category implements Serializable {

public MutableInt id = new MutableInt(-1);

private List<CategorizedItem> categorizedItemList = new ArrayList<CategorizedItem>();

@Transient
public MutableInt getIdAsMutableInt() {
return this.id;
}

@Id
@GeneratedValue
public Integer getId() {
return this.id.intValue();
}

public void setId(Integer id) {
return this.id.setValue(id);
}

@OneToMany(mappedBy="category")
@JoinColumn(name="CATEGORY_ID", insertable=false, updateable=false)
@Cascade(CascadeType.SAVE_UPDATE)
public List<CategorizedItem> getCategorizedItemList() {
return categorizedItemList;
}

// setter's

/**
* Use this method when you have a saved Item
*/
public void addCategorizedItem(CategorizedItem categorizedItem) {
categorizedItem.setCategorizedItemId(new CategorizedItemId(getIdAsMutableInt(), categorizedItem.getItem().getIdAsMutableInt()));
categorizedItem.setCategory(this);

getCategorizedItemList().add(categorizedItem);
}

}

和项目

@Entity
public class Item implements Serializable {

public MutableInt id = new MutableInt(-1);

private List<CategorizedItem> categorizedItemList = new ArrayList<CategorizedItem>();

@Transient
public MutableInt getIdAsMutableInt() {
return this.id;
}

@Id
@GeneratedValue
public Integer getId() {
return this.id.intValue();
}

public void setId(Integer id) {
return this.id.setValue(id);
}

@OneToMany(mappedBy="item")
@JoinColumn(name="ITEM_ID", insertable=false, updateable=false)
@Cascade(CascadeType.SAVE_UPDATE)
public List<CategorizedItem> getCategorizedItemList() {
return this.categorizedItemList;
}

// setter's

/**
* Use this method when you have a saved Category
*/
public void addCategorizedItem(CategorizedItem categorizedItem) {
categorizedItem.setCategorizedItemId(new CategorizedItemId(getIdAsMutableInt(), categorizedItem.getCategory().getIdAsMutableInt()));
categorizedItem.setItem(this);

getCategorizedItemList().add(categorizedItem);
}

}

现在,因为在保存 CategorizedItem 之前您需要categoryId 和 itemId,请执行以下操作

Category category = new new Category();
Item item = new Item();

session.save(new Category());
session.save(new Item());
session.save(new CategorizedItem(userName, category, item));

请注意,只有当您有已保存的类别或已保存的项目时,级联才起作用。否则,您需要按照上面所示的方法进行操作

关于java - Hibernate - 具有附加列的链接表 - 保存在一个事务中,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/3528595/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com