You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Angular Resolver搭配NgRx Store Observable无响应问题排查

NgRx Store结合Resolver无法正常工作排查

我尝试了两种Resolver实现方式:

第一种:不使用Store的版本(可正常工作)

// @Injectable({
//   providedIn: 'root',
// })
// export class EmptyStateResolver implements Resolve<EmptyState> {
//   constructor() {}

//   resolve() {
//     const data = {
//       svg: 'test', // 原代码此处缺失逗号,已补全
//       message: 'To see additional information, please select element from the list',
//       header: `Selected groups: `,
//     };

//     return data;
//   }
// }

第二种:结合NgRx Store Observable的版本(无法正常工作)

组件不显示,且无任何报错信息。调试时Chrome DevTools能在return data语句处停住且有对应值,说明逻辑已触发,但后续无任何反应。

代码实现:

constructor(protected readonly store$: Store) {}

resolve(route: ActivatedRouteSnapshot): Observable<EmptyState> {
  return this.store$.select(selectors.getAllSelectedIDs).pipe(
    map((ids: ID[]) => {
      const data = {
        svg: '',
        message: !ids.length
          ? 'To see additional information, please select element from the list'
          : 'Use toolbar to perform desired actions for selected Items',
        header: `Selected groups: ${ids.length}`,
      };

      return data;
    })
  );
}

问题原因

Angular的Resolver机制要求返回的Observable完成后,才会继续加载目标组件。而NgRx Store的select()方法返回的是一个持续发射值的冷Observable,只要Store中的对应状态发生变化,它就会持续发射新值,永远不会主动完成。这就导致Resolver一直处于等待Observable完成的状态,组件永远无法被渲染。

解决方案

在Observable管道中添加take(1)操作符,只取第一个发射的值后就让Observable完成,这样Resolver就能正常拿到数据并继续流程:

resolve(route: ActivatedRouteSnapshot): Observable<EmptyState> {
  return this.store$.select(selectors.getAllSelectedIDs).pipe(
    take(1), // 添加此操作符
    map((ids: ID[]) => {
      const data = {
        svg: '',
        message: !ids.length
          ? 'To see additional information, please select element from the list'
          : 'Use toolbar to perform desired actions for selected Items',
        header: `Selected groups: ${ids.length}`,
      };

      return data;
    })
  );
}

如果需要确保至少获取到一个值(比如状态可能还未初始化),可以改用first()操作符,它会等待第一个值发射后完成,若Observable永远不发射值则会抛出错误。

内容的提问来源于stack exchange,提问作者Bartek

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.18 19:23:10