danday74
danday74

Reputation: 56936

In ngrx, when dispatching an action is it possible to not trigger the associated effect?

I dispatch my ngrx action with:

store.dispatch(new MyAction(payload));

MyAction has an associated effect. When I dispatch the action the effect fires. Great!

This works as intended. But I only want the effect to fire sometimes. Can you do something like this?

store.dispatch(new MyAction(payload), {triggerEffect: false});

Or do I need to create a second action that is handled exactly the same as MyAction by the reducers and simply not attach an effect to the second Action? I'd rather not go down this route if I can avoid it.

Upvotes: 1

Views: 534

Answers (3)

tlt
tlt

Reputation: 15211

It depends on what are you trying to achieve.

In genera case, without knowing details, i would go for 2 actions. Its simple and clear.

Now, depending on what you are trying to do, there are 2 options:

  1. Have proxy effect that gets an action and based on some property, fires (or not) new action that other effect will handle.

  2. If action data on which you base your decision ends up in state through reducer, then you could use withLatestFrom operator in effects, take latest state and since the order is guaranteed (reducers react first on action and then effects), then you can make your decision based on the state.

Upvotes: 1

Kim Kern
Kim Kern

Reputation: 60357

I don't think there is a built-in solution for this, but you can use a payload property to control the effect execution:

Add the property to your action creator:

class MyAction {
  readonly type = MY_ACTION;
  constructor(private payload: {data: any, shouldTriggerEffect: boolean}) {}
}

Filter the effect:

@Effect()
myAction$ = this.actions$.pipe(
  ofType(ActionTypes.MY_ACTION),
  filter(action => action.payload.shouldTriggerSideEffect),
  // do your stuff
);

Upvotes: 1

spfellers
spfellers

Reputation: 141

Lets say you only want to fire the effect if the payload has a certain property. I would do something like this.

@Effect() myEffect$ = this.action$
    .ofType('ACTION_TYPE')
    .filter(action => action.payload.triggerSideEffect)
    .map( () => Observable.of({type: "DO_SIDE_EFFECT"}));

Upvotes: 2

Related Questions