2

I'm using Angular, ngrx/store and rxjs

So I have a Cart reducer and an Items reducer.

When I'm fetching Items from the API I need to know if they are already in the Cart.

So since I have pagination implemented the best way I thought was to check that in the actual service that fetches Items and creating an InCart field inside the Items object.

I do not want to do it in subscribe because when I'm fetching Items I'm not changing the Cart state so the subscribe will never be called. And if I use map I can't also access the data in the service.

So I'm really not sure on how to do this in a 'Best practice way'.

Probably I could also save the Cart object inside the Cart service in an old fashion way but I don't think that would be the best practice here.

This code below would be the ideal case scenario for me. (But ofc this doesn't work because I can't access the cart object using pluck or map.)

getItems(): Observable<Item[]> {
  return this.http.get(url)
    .map(this.extractData)
    .map(this.extractItemlist)
    .catch(this.handleError)
}

private extractItemlist(res: ApiResponse) {
  switch (res.response.type) {
    case ApiResponse.TYPE.ERROR:
      throw res.response.data.message
    case ApiResponse.TYPE.SUCCESS:
      this.checkIfItemsAreInCart(res.response.data.list)
      return res.response.data.list
  }
}

private checkIfItemsAreInCart(items: Item[]) {
  const cart = this.store.select<CartState>('cart').pluck('cart')

  for (const item of items) {
    for (const cartItem of cart.items) {
      if (item.details.item_id === +cartItem.item_id) {
        item.inCart = true
      } else {
        item.inCart = false
      }
    }
  }
}

Does anyone have idea on how to achieve this? I'm a new to this observables stuff so probably that's why I still didn't came up with a good solution.

I would really appreciate some help.

Frederico Jesus
  • 649
  • 6
  • 14
  • Best practice would be to not use `pluck` and to not pass strings to `select`; see [this answer](https://stackoverflow.com/a/44510829/6680611). And, regarding synchronous access to the store, see [this answer](http://stackoverflow.com/a/42706832/6680611). – cartant Jun 16 '17 at 01:42

1 Answers1

3

I do not want to do it in subscribe because when I'm fetching Items I'm not changing the Cart state so the subscribe will never be called

Subscribe of Observable will be called in first time you call so it does not need "change".

private checkIfItemsAreInCart(items: Item[]) {
  this.store.select<CartState>('cart')
    .take(1)
    .subscribe(cart => {
      for (const item of items) {
         for (const cartItem of cart.items) {
           if (item.details.item_id === +cartItem.item_id) {
             item.inCart = true
           } else {
             item.inCart = false
           }
         }
       }
  });
}
Thien Hoang
  • 625
  • 3
  • 12