代码之家  ›  专栏  ›  技术社区  ›  inorganik

switchMap然后合并不起作用

  •  0
  • inorganik  · 技术社区  · 8 年前

    在我的Angular应用程序中,我路由到一个组件。在这个组件中,我想显示一个 item$ 可观察的。

    现在,如果我的服务有一个缓存项,使用它,不管怎样,从后端请求一个项。因此,体验可能是显示缓存项一段时间,然后后端项在加载后替换它。如果该项在后端不存在,则缓存的项将是唯一发出的值。如果不是,我们会显示一个“未找到”。

    以下是我如何执行的:

      ngOnInit() {
        this.item$ = this.route.paramMap.pipe(
          switchMap((params: ParamMap) => {
            this.id = params.get('id'); // get the id
            if (this.service.item && this.id === this.service.item.id) {
              return of(this.service.item); // cached item
            }
            return of(null); // nothing cached
          }),
          merge(this.backend.getItem(this.id)) // get backend item
        );
      }
    

    我的模板代码

    <div *ngIf="item$ | async as item; else showNotFound">
      <p>{{ item.name }}</p>
      <!-- other props omitted -->
    </div>
    <ng-template #showNotFound>
      <p>Not found</p>
    </ng-template>
    

    但是,merge在switchMap之前激发,无法获取该项,因为 this.id 尚未设置。如果我将合并移到switchMap前面,switchMap将无法获取参数。如何做到这一点?

    2 回复  |  直到 8 年前
        1
  •  0
  •   Eliseo    8 年前

    我知道你想写信

    ngOnInit() {
        this.route.paramMap.pipe(
          switchMap((params: ParamMap) => {
            this.id = params.get('id'); // get the id
            if (this.service.item && this.id === this.service.item.id) {
              return of(this.service.item); // cached item
            }  
            //If not is cached
            return this.backend.getItem(this.id)
              //You can "cached" the value, here
              .pipe(tap((item)=>{this.service.item=item}
              ));
          })).subscribe((item)=>{this.item=item}); //DON'T forget subscribe
      }
    
        2
  •  0
  •   inorganik    8 年前

    我可以这样做:

      ngOnInit() {
        this.item$ = this.route.paramMap.pipe(
          switchMap((params: ParamMap) => {
            this.id = params.get('id'); // get the id
            return this.backend.getItem(this.id).pipe(
              map(backendResult => {
                if (backendResult === undefined) {
                  if (this.service.item && this.id === this.service.item.id) {
                    return this.service.item; // cached item
                  }
                  return null; // nothing cached
                } else {
                  return backendResult;
                }
              })
            );
          }),
        );
      }