Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Do something when an action has been dispatched

Tags:

angular

ngxs

Let's say we an action SyncUserData, which returns observable that listen to changes from the database. Whenever there's a change, the action dispatches the action new PatchUserData(newData).

The SyncUserData action is dispatched (only once) from ngxsOnInit of the state.

In a different section (e.g., component), I want to do something whenever the action PatchUserData is dispatching. Something like this:

this.store.onDispatch(PatchUserData).subscribe();

I was looking a bit in the source, and I didn't find something similar to my example.

like image 480
Eliya Cohen Avatar asked Sep 23 '18 07:09

Eliya Cohen


People also ask

What happens when you try to dispatch an action within a reducer?

Dispatching an action within a reducer is an anti-pattern. Your reducer should be without side effects, simply digesting the action payload and returning a new state object. Adding listeners and dispatching actions within the reducer can lead to chained actions and other side effects.

Can a Redux action dispatch another action?

Dispatch actions using Redux-saga library To run many async instructions one after the other and also maintain readability of the code, we can dispatch an action that will then trigger a saga. We can use redux-saga library in the same way. Using the saga, we can dispatch actions with the put effect.

How do you dispatch actions in Saga?

Create a plain JavaScript Object to instruct the middleware that we need to dispatch some action, and let the middleware perform the real dispatch. This way we can test the Generator's dispatch in the same way: by inspecting the yielded Effect and making sure it contains the correct instructions.


2 Answers

An alternative to subscribing to the state directly is to use the NGXS action stream to be notified when a specific action has been dispatched/completed see the documentation for action handlers.

From the official doco:

@Component({ ... })
export class CartComponent {
  constructor(private actions$: Actions) {}

  ngOnInit() {
    this.actions$.pipe(ofActionSuccessful(CartDelete)).subscribe(() => alert('Item deleted'));
  }
}
like image 163
Garth Mason Avatar answered Nov 11 '22 00:11

Garth Mason


You don't need to subscribe to a certain event in your case, you can subscribe to userData in your store and have the lastest version of it no matter whatever action changed it. Modify next sample according to your data models and subscribe to observable:

import { Select } from '@ngxs/store';

@Select(({ userData }: AppState) => userData)
  userData$!: Observable<UserData>;

More on select: https://ngxs.gitbook.io/ngxs/concepts/select

like image 24
Yevgen Avatar answered Nov 11 '22 02:11

Yevgen