spring-data-mongodb
spring-data-mongodb copied to clipboard
Attempts to update a lazy object result in the creation of a new object rather than modifying the existing one.
I have a user document that has a reference to subgroups as lazy. I am trying to get a subgroup from the user and then try to modify it but instead of updating it tries to insert a new one. This is only the case when I add the auditing field @Version version. If I removed the version field, everything work fine and it update the document.
// PostConstruct
public void test() {
setup(); // setting update test data
executeOperation();
}
private void executeOperation() {
final User user = userRepository.findById("1").get();
user.getSubTree().getChildren().add(subRepository.findById("p1").get());
nodeService.save(user.getSubTree());
}
private void setup() {
final MongoUser user = new MongoUser("1");
user.setName("test");
final MongoUser savedUser = userRepository.save(user);
final MongoSubGroup group = new MongoSubGroup();
group.setId("BASE");
group.setOwner(savedUser);
group.setName("BASE");
subGroupRepository.save(group);
final Dept mongoDepartment = new MongoDept("dept1");
final Dept savedDepartment = deptRepository.save(mongoDepartment);
final MongoSub profile = new MongoSub();
profile.setId("p1");
profile.setOwner(savedDepartment);
subRepository.save(profile);
}`
From executeOperation() there is a lazy load operation for subgroups and then there is a call to nodeservice
public void save(SubGroup subgrup) {
for (SubTreeNode node : subgrup.getChildren()) {
// skipping Some business logic
final Link link = new Link();
link.setId("1");
((MongoSubGroup) (subgrup)).getLinks().add(link);
}
groupRepository.save(subgrup);
}
So here as soon groupRepository.save(subgrup) tries to create a new one and as id as the index it gives duplicate error
Caused by: com.mongodb.MongoWriteException: Write operation error on server localhost:27017. Write error: WriteError{code=11000, message='E11000 duplicate key error collection: demo.subGroup index: _id_ dup key: { _id: "BASE" }', details={}}.
Attached sample project demo.zip
Thanks for reporting and the reproducer project - we'll have a look!
While saving lazy loading references back as such is supported, storing them back as entities is currently not. The entire szenario is related to #2306 which had been declined some years ago. Nevertheless we think it's worth revisting the past decission and investigate potential solutions like unwrapping proxies before save operations.
@christophstrob By removing the version property, mongo modifies the document. So not sure even though object is lazy without versioning it's working
it's a matter of accessing properties to determine if an entity is new or not that then leads to different routes within the template as versioned ones need more treatment.
it's a matter of accessing properties to determine if an entity is new or not that then leads to different routes within the template as versioned ones need more treatment.
Any updates on the fix?