在我的面向团队的应用程序中,我在User和Team之间有多对多的关系,因此hibernate创建了关联表。问题是,在更新了具有Team的用户之后,hibernate会从USER_TEAM表中删除相应的关联记录。
用户实体:
@Entity
@Table(name="USERS")
public class User extends SelectItem {
@Id
@Column(name="EMAIL")
private String email;
@Column(name="PASSWORD")
private String password;
@Column(name="NAME")
private String name;
@Column(name="GROUPNAME")
private String group;
@ManyToMany(
targetEntity=Team.class
)
@ForeignKey(name="FK_TEAM_TO_USER", inverseName = "FK_USER_TO_TEAM")
@JoinTable(
name="USER_TEAM",
joinColumns=@JoinColumn(name="EMAIL"),
inverseJoinColumns=@JoinColumn(name="TEAMNAME")
)
@LazyCollection(LazyCollectionOption.FALSE)
private List<Team> teamList;
@OneToMany(
fetch = FetchType.EAGER,
mappedBy="user")
private List<Invitation> invitationList;
//getters setters
团队实体:
@Entity
@Table(name="TEAM")
public class Team extends SelectItem {
@Id
@Column(name="TEAMNAME")
private String name;
@ManyToOne
@ForeignKey(name="FK_TEAM_TO_TEAMLEADER")
@JoinColumn(name="TEAMLEADER")
private User teamLeader;
@ManyToMany(
mappedBy = "teamList",
targetEntity = User.class
)
@LazyCollection(LazyCollectionOption.FALSE)
private List<User> memberList;
//getters setters
这是日志:
INFO:20.11.2012 22:50:00,170 DEBUG org.hibernate.transaction.JDBCTransaction.begin:begin
INFO:20.11.2012 22:50:00,175 DEBUG org.hibernate.transaction.JDBCTransaction.begin:当前自动提交状态:true
信息:20.11.2012 22:50:00,175 DEBUG org.hibernate.transaction.JDBCTransaction.begin:禁用自动提交
INFO:20.11.2012 22:50:00,175 DEBUG hibernate.jdbc.util.SQLStatementLogger.logStatement:从USERS user_中选择user_.EMAIL,user_.GROUPNAME为GROUPNAME0_,user_.NAME为NAME0_,user_.PASSWORD为PASSWORD0_,其中user_.EMAIL =?
INFO:Hibernate:从USERS user_选择user_.EMAIL,user_.GROUPNAME为GROUPNAME0_,user_.NAME为NAME0_,user_.PASSWORD为PASSWORD0_,其中user_.EMAIL =?
INFO:20.11.2012 22:50:00,176 TRACE type.descriptor.sql.BasicBinder.bind:binding parameter [1] as [VARCHAR] - a@b.com
信息:20.11.2012 22:50:00,177 TRACE type.descriptor.sql.BasicExtractor.extract:找到[users]列[GROUPNAME0_]
信息:20.11.2012 22:50:00,178 TRACE type.descriptor.sql.BasicExtractor.extract:找到[default]作为列[NAME0_]
INFO:20.11.2012 22:50:00,178 TRACE type.descriptor.sql.BasicExtractor.extract:找到[default]作为列[PASSWORD0_]
INFO:20.11.2012 22:50:00,251 DEBUG org.hibernate.transaction.JDBCTransaction.commit:commit
INFO:20.11.2012 22:50:00,252 DEBUG hibernate.jdbc.util.SQLStatementLogger.logStatement:更新USERS设置GROUPNAME =?,NAME =?,PASSWORD =? EMAIL =?的地方 INFO:Hibernate:更新USERS设置GROUPNAME =?,NAME =?,PASSWORD =?哪里有EMAIL =?
INFO:20.11.2012 22:50:00,260 TRACE type.descriptor.sql.BasicBinder.bind:binding parameter [1] as [VARCHAR] - 用户
INFO:20.11.2012 22:50:00,261 TRACE type.descriptor.sql.BasicBinder.bind:binding parameter [2] as [VARCHAR] - andy
INFO:20.11.2012 22:50:00,261 TRACE type.descriptor.sql.BasicBinder.bind:binding parameter [3] as [VARCHAR] - break
INFO:20.11.2012 22:50:00,262 TRACE type.descriptor.sql.BasicBinder.bind:binding parameter [4] as [VARCHAR] - a@b.com
INFO:20.11.2012 22:50:00,264 DEBUG hibernate.jdbc.util.SQLStatementLogger.logStatement:从USER_TEAM中删除EMAIL =? 信息:休眠:从USER_TEAM删除,其中EMAIL =?
INFO:20.11.2012 22:50:00,271 TRACE type.descriptor.sql.BasicBinder.bind:binding parameter [1] as [VARCHAR] - a@b.com
信息:20.11.2012 22:50:00,274 DEBUG
org.hibernate.transaction.JDBCTransaction.toggleAutoCommit:重新启用自动提交 信息:20.11.2012 22:50:00,274 DEBUG org.hibernate.transaction.JDBCTransaction.commit:已提交的JDBC连接
更新操作由Spring的hibernateTemplate以UserDAO中的这个简单方法提供:
public void saveUser(User user){
hibernateTemplate.saveOrUpdate(user);
}
(我知道不应该使用hibernateTemplate,但我认为这不是这个问题的重点)
在Spring事务服务bean UserServiceImpl:
中简单地在事务中调用DAO方法@Transactional(readOnly=false)
public void saveUser(User user){
userDao.saveUser(user);
}
正如你所看到的,我没有任何级联注释,在更新中我当然不会改变用户的PK(EMAIL),所以我不明白这种行为。我正在使用spring 3.1.0.RELEASE和hibernate 3.6.10.Final。
感谢您的任何建议或解释。
答案 0 :(得分:5)
你不需要任何级联来实现这一点。给定用户的连接表的内容由该用户的teamList
集合的内容确定。因此,如果您使用具有空团队列表的用户调用saveOrUpdate()
,Hibernate将删除此用户的连接表的内容。