【问题标题】:Rxjs Observable IssueRxjs 可观察到的问题
【发布时间】:2020-06-11 02:11:31
【问题描述】:

我已经声明了一个服务中的主题,并尝试通过使用“subject.next()”对后端进行 GET 调用来推送响应。还使用“subject.asObservable()”为该主题分配了一个可观察对象并订阅了两个不同组件(父级和路由器出口子级)中的 observable。问题是 observable 只为一个订阅者而不是为两个订阅者发出新值。

服务

  subject = new Subject<any>();
  observable = this.subject.asObservable();


 public getDetails(id) {
    return this.http.get(this.url.concat(id))
      .pipe(map(data => this.extractDetails(data),
            catchError(err => this.handleError(err)));
  }
 public extractDetails(data){
    this.subject.next(data);
    return data;
  }

父组件

ngOnInIt(){
 this.hitUrl();

}
getDetails(){
    this.service.observable.subscribe(
      (data: any) => {
        console.log(data);
      },
      err => {
        console.error(err);
      }
    )
  }

  hitUrl(id: string) {
    this.service.getDetails(id).subscribe(
      (data: any) => 
        if(!!data){
            console.log(data);
            this.getDetails();
          }
      },
      err => {
        console.log(err);
      }
    );
  }

路由器插座子组件

ngOnInIt(){
 this.hitUrl();

}
getDetails(){
    this.service.observable.subscribe(
      (data: any) => {
        console.log(data);
      },
      err => {
        console.error(err);
      }
    )
  }

  hitUrl(id: string) {
    this.service.getDetails(id).subscribe(
      (data: any) => 
        if(!!data){
            console.log(data);
            this.getDetails();
          }
      },ngOnInIt(){
 this.hitUrl();

}
getDetails(){
    this.service.observable.subscribe(
      (data: any) => {
        console.log(data);
      },
      err => {
        console.error(err);
      }
    )
  }

  hitUrl(id: string) {
    this.service.getDetails(id).subscribe(
      (data: any) => 
        if(!!data){
            console.log(data);
            this.getDetails();
          }
      },
      err => {
        console.log(err);
      }
    );
  }

      err => {
        console.log(err);
      }
    );
  }


在组件中,hitUrl() 也会在执行调用操作时触发,然后我需要 observable 向两个订阅者发出最新数据(如果调用操作是从父级或路由器出口子级执行的)。

【问题讨论】:

  • 为什么在你的案例中还需要一个主题?您可以在两个组件中直接订阅 http 请求。
  • 两个行动号召都在一个页面中(网页视图)..如果其中一个被调用,那么另一个也应该得到更新(“关注”应该更改为“关注”)..跨度>
  • 在每个 ngOnInits 中放置 getDetails() 调用。这就是你的组件订阅 observables 的方式
  • 尝试使用 'tap' 方法而不是服务中的地图。当我们想要更改数据时,我们使用地图。
  • 在两个组件 ngOnInits 中调用 getDetails()...

标签: angular typescript rxjs rxjs-observables


【解决方案1】:

我从您的问题中了解到的是,您有两个组件和一个服务,您正在使用服务获取数据,并且希望在调用以下“getDetails()”函数时同时将数据发送到两个组件,而不管从哪里调用这个函数。它可能是调用函数的父级或子级。

 public getDetails(id) {
     return this.http.get(this.url.concat(id))
       .pipe(map(data => this.extractDetails(data),
             catchError(err => this.handleError(err)));   }

在您的代码中,问题在于您正在调用 getDetails 函数的组件代码,而在该函数内部您订阅了 observable,而您应该在 ngOnInit 中订阅 observable。这样当从服务中调用这个 observable.next 时,observable 将在两个组件中执行,因为它将在那里被订阅,请参见下面的代码。

 ngOnInit(){
     this.getDetails();
     this.hitUrl();   }

 getDetails(){
   this.service.observable.subscribe(
     (data: any) => {
       console.log(data);
     },
     err => {
       console.error(err);
     }
   )   
 }

 hitUrl(id: string) {
   this.service.getDetails(id).subscribe(
     (data: any) => 
       if(!!data){
           console.log(data);
         }
     },
     err => {
       console.log(err);
     }
     );   
 }

在上面的代码中,我们首先订阅了主题,然后我们调用了数据。在 service 中的 getDetails(id) 函数中,我们已经发出了主题,并替换了 service 中的以下行。

subject = new Subject<any>();
  observable = this.subject.asObservable();

以下

subject = new BehaviorSubject({});

希望这会有所帮助...

【讨论】:

  • 我做了你建议的所有改变,但没有奏效
  • 将getDetails()中的“this.service.observable.subscribe”这一行改为“this.service.subject.subscribe(”
猜你喜欢
  • 1970-01-01
  • 2018-07-30
  • 2019-12-10
  • 1970-01-01
  • 2019-10-18
  • 2016-05-17
  • 2017-06-11
  • 2016-10-29
  • 1970-01-01
相关资源
最近更新 更多