java spring data mongodb无法在未设置id的子对象上执行级联保存
我正在使用@CascadeSave将子对象保存在单独的集合中。 我的文档类是:
public class FbUserProfile{
@Id
private long id;
@DBRef(lazy=true)
@CascadeSave()
private Set<FacebookFriend> friends;
@DBRef(lazy=true)
@CascadeSave()
private Set<FacebookFriendList> customFriendList;
}
public class FacebookFriend{
@Id
private long id;
private String name;
}
public class FacebookFriendList{
@Id
private long id;
private String name;
private String list_type;
}
我在两个朋友、customFriendList中都添加了一些对象。 并尝试使用以下命令更新fbUserProfile对象:
mongoTemplate.save(fbUserProfile);
note: fbUserProfile already exists in db. Now I am updating this
Error Message: Cannot perform cascade save on child object without id set
如果我删除@CascadeSave。这对我来说很好。如何级联设置对象。 我还将@CascadeSave用于其他对象。工作正常,但它们不是设定的对象
# 1 楼答案
好的,我扩展该类,它将检查文档是否存在如果它存在,它将更新文档,否则它将插入文档:
# 2 楼答案
在依赖子对象上设置ID的最佳方法是通过扩展AbstractMongoEventListener类并重写onConvert()方法来编写侦听器类
# 3 楼答案
我在其他地方找到了相同的教程:Baeldung和JavaCodeGeeks(这是我遵循的教程)
我也遇到过同样的问题,我可以解决它
当您试图持久化一个集合时,就会发生这种情况。集合的项是否有@Id并不重要,因为集合本身不会有@Id。我在EventListener的onBeforeConvert中编辑了代码,以检查您试图保存的字段是否是一个集合(在我的示例中是一个列表)。如果它是一个列表,您只需在其中循环检查每个项目的@Id并保存它们
如果它不是一个集合,您仍然必须像以前一样持久化它们
# 4 楼答案
如果您有列表,上述解决方案可以很好地工作。但是我们可以避免为列表中的每个元素触发save查询,因为这会降低性能。下面是我从上述代码中找到的解决方案