I am iterating over a list of objects and saving one object at a time after each loop. What i found is that only the last object is always saved when using the MongoRepository interface.

for instance

for(int i=0;i<=objectList.size();i++){
    repositoryInterface.save(objectList.get(i));
}

In this case,only the last object is saved when there are about 3 objects in objectList.

Again, if repositoryInterface is used to save all the objectList in one query, say, repositoryInterface.save(objectList), only the last changes to the last object in objectList is persisted for all three objects in objectList. For instance,

public class Book {
    private String bookName;
    private int bookNumber;
    //then getters and setters
}


List<Book> books = new ArrayList<>();
Book book0 = new Book();
book0.setBookName("Book0");
book0.setBookNumber(0);

books.add(book0);

Book book1 = new Book();
book1.setBookName("Book1");
book1.setBookNumber(1);

books.add(book1);

for(int i=0;i< books.size();i++){
    switch(i){
        case 0 :  
            books.get(0).setBookNumber(00);
            break;
        case 1 :
            books.get(1).setBookNumber(11);
            break;
        default:
            System.out.println("nothing per this example");
    }
}

repositoryInterface.save(books);

now checking the mongo database,what is inserted is

{bookName:"Book0",bookNumber:11},{bookName:"Book1",bookNumber:11} 

instead of

{bookName:"Book0",bookNumber:00},{bookName:"Book1",bookNumber:11}
3

There are 3 answers

0
Jens Schauder On BEST ANSWER

If one fixes some basic issues with the code it works just fine. Here is the code I tried to reproduce the issue, but which runs without a problem (package and import statements excluded):

The Book class:

public class Book {
    private String bookName;
    private int bookNumber;

    public String getBookName() {
        return bookName;
    }

    public void setBookName(String bookName) {
        this.bookName = bookName;
    }

    public int getBookNumber() {
        return bookNumber;
    }

    public void setBookNumber(int bookNumber) {
        this.bookNumber = bookNumber;
    }
}

The RepositoryInterface

public interface RepositoryInterface extends MongoRepository<Book, String>{

}

The Bean containing the actual code to execute. Use either method in doSomething in order to process the books one by one or as a single list.

@Component
public class RunCode {

    private final RepositoryInterface repositoryInterface;

    public RunCode(RepositoryInterface repositoryInterface) {
        this.repositoryInterface = repositoryInterface;
    }

    @PostConstruct
    public void doSomething() {
       // updateAsList();
        updateOneByOne();
    }

    private void updateOneByOne() {
        List<Book> books = createBookList();
        for(int i=0;i<books.size();i++){
            repositoryInterface.save(books.get(i));
        }
    }

    private void updateAsList() {
        List<Book> books = createBookList();

        for (int i = 0; i < books.size(); i++) {
            switch (i) {
                case 0:
                    books.get(0).setBookNumber(00);
                    break;
                case 1:
                    books.get(1).setBookNumber(11);
                    break;
                default:
                    System.out.println("nothing per this example");
            }
        }

        repositoryInterface.save(books);
    }

    private List<Book> createBookList() {
        List<Book> books = new ArrayList<>();
        Book book0 = new Book();
        book0.setBookName("Book0");
        book0.setBookNumber(0);

        books.add(book0);

        Book book1 = new Book();
        book1.setBookName("Book1");
        book1.setBookNumber(1);

        books.add(book1);
        return books;
    }
}
0
Darren On

For those of you with similar problems, my error was that the @Id for each of the items in the list was the same, so I had to create @Embeddable class with the primary keys I wanted to use to be unique. then used the @EmbeddedId annotation on the class in the main Entity object.

So essentially what was happening for me was it was inserting the first object, but because the other objects' ids were exactly the same, it was updated by that id. This is why I would only ever see the last value.

0
samslow On

Why don't you use saveAll()instead of save()?

saveAll() provide save entity, All of list from input.