我在尝试更新“照片”时遇到错误:
Photo photo = photoRepository.findById(id);
List<Photo> photos = user.getPhotos();
user.setPhotos(photos.add(photo));
userRepository.update(user);
显示以下错误:
Different object with same identifier was already associated with the session
看来,具有相同标识符的不同对象(第一行:第一行中的照片,第二行:user.getPhotos()中的照片)。
所以,我无法更新我的用户。 我怎么能避免这个错误?
userRepository:
tx = session.beginTransaction();
user = (User) session.get(User.class, id);
session.getTransaction().commit();
答案 0 :(得分:0)
您的代码存在缺陷,在ORM世界中管理双向关系时,您绝不允许对内部状态进行外部修改。目前,您正在使用一种服务方法,即从用户中提取照片列表并添加新照片。有了这个你只设置关系的一面。您还应该在setUser
对象上调用Photo
。
Photo photo = photoRepository.findById(id);
List<Photo> photos = user.getPhotos();
photo.setUser(user);
user.setPhotos(photos.add(photo));
userRepository.update(user);
但是这段代码容易出错,应该在User
旁边的setPhotos
对象内,你不应该允许public class User {
public Set<Photo> getPhotos() {
// Unmodifiable to protect internal state.
return Collections.unmodifiableSet(this.photos);
}
// No setPhotos!
public void addPhoto(Photo photo) {
photo.setUser(this);
this.photos.add(photo);
}
}
被调用,因为这可能会破坏所有正确的关系。
Photo
假设您的User
与setUser
位于同一个包中,public
可以是包可见的(即{{1}上没有protected
或setUser
}} 方法)。
现在,您可以在代码中执行
Photo photo = photoRepository.findById(id);
user.addPhoto(photo);
userRepository.update(user);
无需使其更复杂,添加照片的逻辑现在已经很好地封装和测试。