Calling observables synchronously one after anothe

2020-04-24 16:58发布

问题:

I have the following service calls available:
productService.GetAllProducts()
productService.DeleteProduct()
productService.GetCategories()
productService.DeleteCategory()

In sudo code I need to do the following in my component:

  1. Get a list of products using productService.GetAllProducts().

  2. Loop through the list of products and call productService.DeleteProduct() for each product.

  3. Once I can confirm the above deletes are all complete (due to db constraints) I need to then get a list of categories using productService.GetCategories(). Loop through each category and call productService.DeleteCategory().

I am aware that my life would be a lot easier if I had better backend calls to do bulk deletes, but I do not have a choice in this case. I need to follow the pattern of getting a list, looping through it, doing an individual delete one each item.

Is it even possible doing what I am trying to do using flatMap and the observable complete param? My biggest problem is knowing when the code is finished deleting all of the products before searching for and deleting all of the categories.

回答1:

You may want to try something along these lines

productService.GetAllProducts()
.switchMap(
   products => forkJoin(products.map(product => productService.DeleteProduct(product)))
)
.switchMap(() => productService.GetCategories())
.switchMap(
   categories => forkJoin(categories.map(category => productService.DeleteCategory(category)))
)
.subscribe(() => console.log('done'))

The whole idea is the following

  • GetAllProducts returns an array of Products which is passed as parameter to the first switchMap
  • The Products array is transformed, via map, into an array of Observables which are the result of DeleteProduct - the array of Observable is passed to the first forkJoin as its parameter
  • forkJoin emits when all the Observables it has received as parameter complete, and therefore will emit when all the Products have been deleted
  • The same reasoning is repeated for categories

I am not sure the code is syntactically perfect, but it should be enough to give you an idea on how to proceed.