Intro
I will try inserting and update in this time.
Inserting and updating data
In simple cases, I can override method like below.
CategoryRepository.java
packagemicronaut.sample.posts;importio.micronaut.data.annotation.Join;importio.micronaut.data.annotation.Query;importio.micronaut.data.model.query.builder.sql.Dialect;importio.micronaut.data.r2dbc.annotation.R2dbcRepository;importio.micronaut.data.repository.reactive.ReactiveStreamsCrudRepository;importmicronaut.sample.posts.dto.SearchCategory;importreactor.core.publisher.Flux;importreactor.core.publisher.Mono;@R2dbcRepository(dialect=Dialect.SQL_SERVER)publicinterfaceCategoryRepositoryextendsReactiveStreamsCrudRepository<Category,Long>{...// Insert@OverrideMono<Category>save(Categorycategory);// Update@OverrideMono<Category>update(Categorycategory);}
Because "save" and "update" don't differetiate whether the model class data is newly created or retrieved from the DB, So I must use them properly.
PostService.java
packagemicronaut.sample.posts;importjava.time.LocalDateTime;importio.micronaut.transaction.annotation.Transactional;importjakarta.inject.Singleton;importmicronaut.sample.posts.dto.SearchCategory;importmicronaut.sample.users.UserRepository;importreactor.core.publisher.Flux;importreactor.core.publisher.Mono;@SingletonpublicclassPostService{privatefinalPostRepositoryposts;privatefinalCategoryRepositorycategories;privatefinalUserRepositoryusers;publicPostService(PostRepositoryposts,CategoryRepositorycategories,UserRepositoryusers){this.posts=posts;this.categories=categories;this.users=users;}...publicMono<String>updateCategory(StringcategoryName){returncategories.findByName(categoryName).flatMap(c->{c.setLastUpdateDate(LocalDateTime.now());// Don't do this because this insert new "Category" data.// I should write "categories.update(c)";returncategories.save(c);}).switchIfEmpty(Mono.defer(()->{Categoryc=newCategory();c.setName(categoryName);c.setLastUpdateDate(LocalDateTime.now());returncategories.save(c);})).map(c->"OK");}}
Insert data into multiple tables
Unlike Entity Framework Core, they don't automatically insert or update data into relational tables.
Therefore, each data must be inserted or updated in order.
PostService.java
packagemicronaut.sample.posts;importjava.time.LocalDateTime;importio.micronaut.transaction.annotation.Transactional;importjakarta.inject.Singleton;importmicronaut.sample.posts.dto.SearchCategory;importmicronaut.sample.users.UserRepository;importreactor.core.publisher.Flux;importreactor.core.publisher.Mono;@SingletonpublicclassPostService{...publicMono<String>addSamplePost(Stringtitle,Stringcontents,StringcategoryName){returncategories.findByName(categoryName).map(c->{PostnewPost=newPost();newPost.setTitle(title);newPost.setContents(contents);newPost.setCategories(c);newPost.setLastUpdateDate(LocalDateTime.now());returnnewPost;}).switchIfEmpty(Mono.defer(()->{Categoryc=newCategory();c.setName(categoryName);c.setLastUpdateDate(LocalDateTime.now());// Insert new "Category" datareturncategories.save(c).map(newCategory->{PostnewPost=newPost();newPost.setTitle(title);newPost.setContents(contents);newPost.setCategories(newCategory);newPost.setLastUpdateDate(LocalDateTime.now());returnnewPost;});})).flatMap(p->users.findById(1L).map(u->{p.setUsers(u);returnp;})).flatMap(p->// Insert new "Post" dataposts.save(p).map(pst->"OK: "+pst.getId()));}}
Transaction
When the program cases some exceptions on inserting and updating data, I want to rollback.
To do this, I can add a "@Transactional" annotation.
...// Add this@Transactional()publicMono<String>updateCategory(StringcategoryName){returncategories.findByName(categoryName).flatMap(c->{c.setLastUpdateDate(LocalDateTime.now());returncategories.update(c);}).switchIfEmpty(Mono.defer(()->{Categoryc=newCategory();c.setName(categoryName);c.setLastUpdateDate(LocalDateTime.now());returncategories.save(c);})).flatMap(c->{// Intentionally raise an exception to validate the rollbackc.setName(null);c.setLastUpdateDate(LocalDateTime.now());returncategories.update(c);}).map(c->"OK");// Don't add this line// .onErrorResume(e -> Mono.just(e.getMessage()));}}
In this code, I must not add "onErrorResume".
If I add it, rollback is not performed because exception occurrence cannot be detected.
Top comments(0)
For further actions, you may consider blocking this person and/orreporting abuse