如何从ngrx选择器的可观察获取中获取原始数据

时间:2019-10-03 15:22:55

标签: angular typescript observable ngrx ngrx-store

我在我的项目中使用了很棒的ngrx商店管理库。因此,要在组件中获取数据,我正在使用ngrx / store中的@Select(),并且此函数返回可观察到的值。目前,我很难从可观察的

获取原始数据

在我的代码中,observable返回的是我在HTML表中显示的用户详细信息列表。该表具有诸如排序,过滤之类的功能。困难在于根据我在表中显示的列对数据进行排序,为此,我想获取原始数据而不是可观察的排序。

@Select(UserState.userList) userList$; 

<thead>
    <tr>
        <td (click)="sortByName()">
            Name
        </td>

        <td>
            Address
        </td>
    </tr>
</thead>

<tbody>
    <tr *ngFor="let user of userList$ | async">
        <td>
            {{user.name}}
        </td>

        <td>
            {{user.address}}
        </td>
    </tr>
</tbody>

我的问题是如何根据名称对可观察对象进行排序:

sortByName(){
  this.userList$ = this.userList$.sort((a,b)=>{

  return 
 }
}

请注意,我将在提交表单后调度该动作:

submit() {
    if (this.searchForm.valid) {
    this.store.dispatch(new GET_USER_LIST());
   }
  } 

我尝试使用地图运算符,但对我而言不起作用。

请建议我如何实现这一目标。

2 个答案:

答案 0 :(得分:0)

您可以将map rxjs操作符(而不是map js函数!)与js sort()一起使用,例如:

this.users = this.userList$
  .pipe(
     map((users) => users.sort((a,b) => a.name.toLowerCase() > b.name.toLowerCase() ? -1 : 1))
  );

答案 1 :(得分:0)

您说您尝试过地图操作符,但未显示尝试。 Map应该适合您的用例。

有很多方法可以做到这一点,一种方法是创建一个新的可观察到的,可从userList $派生的对象,并使事物保持反应性,您可以使用主题来跟踪排序标准。

sortedList$: Observable<User>;
sortBy$: Subject<string> = new Subject<string>();
constructor() { 
  this.sortedList$ = this.userList$.pipe(
    latestFrom(sortBy$), 
    map(([users, sortBy]) => { 
     // here you have access to users and the sortBy string.
     // do your sorting and return the sorted user list. 
    })); 
}

sortByName(): void { this.sortBy$.next('name') }

然后,您可以在模板中使用异步管道订阅sortedList $。

执行此操作的另一种方法是,由于您已经在使用NGXS,因此将排序状态添加到商店中,并创建一个将userList选择器和您的排序选择器组合在一起的选择器,并返回已排序的列表。