1

I am trying to learn spring webflux. In ReactiveMongoRepository, I am trying to check if category already exists. If it already exists then return that object otherwise save and return new saved object. Something like following.

public Mono<Category> save(Category category) {
    final Mono<Category> byId = repository.findById(category.getId());
    final Category block = byId.block();
    if (block == null) {
        return repository.save(new Category(category.getName()));
    } else {
        return byId;
    }
}

How can I do this without using block()?

1
  • 1
    Use switchIfEmtpy instead of block. Commented Apr 21, 2020 at 10:20

3 Answers 3

1

Use Mono::switchIfEmpty that provides an alternative Mono in case the former one is completed without data. As long as ReactiveMongoRepository::save returns Mono, you can pass it to generate the alternative one.

return repository.findById(category.getId())
                 .switchIfEmpty(repository.save(new Category(category.getName())));

In case ReactiveMongoRepository::findById returns a Mono with data, the Mono::switchIfEmpty will not be called.

Edit: Using Mono::defer with a Supplier<Mono> makes the saving operation to be delayed when necessary:

.switchIfEmpty(Mono.defer(() -> repository.save(new Category(category.getName()))));
Sign up to request clarification or add additional context in comments.

2 Comments

This is not totally correct. respository.save will be called eagerly.
Yes. The Mono with the result is returned immediately upon calling the save method and using Mono::defer should help. The question was about using avoiding block() operation. However, a good point!
1

You can try something like this

public Mono<Category> getCategories(Category category) {
   return repository.findByName(category.getName()).doOnNext(o -> {
   }).switchIfEmpty(repository.save(category));
}

Comments

0

You need to defer the switchIfEmpty. Otherwise, it'll be triggered eagerly:

return repository.findById(category.getId())
                 .switchIfEmpty(Mono.defer(() ->respository.save(category)));

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.