Search code examples
javascriptangularrxjsngrxngrx-store

Update ngrx selector inside ngOnChanges


I have a parent component (B) that is getting data from it's parent input (A) (C) have is (B) child component.

Inside (B) I'm having a selector that gets data from the store.

export class BComponent implements OnChanges {
    @Input() branchId;

  ngOnChanges() {
    this.selectedDataByBranch$ = this.store.pipe(
      select(selectBranchDirections, { branchId: this.branchId, dir: this.selectedDirection })
    );
    this.selectedDataByBranch$.subscribe(selectedDataByBranch => {
      this.trainsDatasets = this.getDatasets(selectedDataByBranch);
      this.lineChart.data.datasets = this.trainsDatasets ? this.trainsDatasets : [];
      this.lineChart.update();
    });
  directionChanged(event) {
    this.selectedDirection = event;
    this.selectedDataByBranch$ = this.store.pipe(
    select(selectBranchDirections, { branchId: this.branchId, dir: this.selectedDirection })
   );
  }
}

directionChanged is the Output event that I get from (C)

The issue this that selectedDataByBranch subscription is not getting the new data update triggered inside selectedDataByBranch$

I have also tried this way

directionChanged(event) {
   this.selectedDirection = event;

  select(selectBranchDirections, { branchId: this.branchId, dir: this.selectedDirection });
}

Solution

  • What i could suggest is. Turn your parameters into a Subject then merge with the store selection, in your directionChanged(event) method provide value to subject.

    So your final code will be something like this:

    export class BComponent implements OnChanges {
        @Input() branchId;
        criterias$= new Subject<{branchId:number,dir:number}>;
        ngOnChanges() {
          this.selectedDataByBranch$ = this.criterias$.pipe(mergeMap(criteria=> this.store.pipe(
          select(selectBranchDirections, { branchId: criteria.branchId, dir: this.searchDirection})
        )));    
    
        this.selectedDataByBranch$.subscribe(selectedDataByBranch => {
          this.trainsDatasets = this.getDatasets(selectedDataByBranch);
          this.lineChart.data.datasets = this.trainsDatasets ? this.trainsDatasets : [];
          this.lineChart.update();
        });
        this.criterias$.next({branchId:this.branchId,dir:this.sortDirection}); // init first call
       }    
      directionChanged(event) {
        this.selectedDirection = event;
        this.criterias$.next({ branchId: criteria.branchId, dir: this.searchDirection}});
       );
      }
    }
    

    This stackblitz tries to materialize what i say.