【问题标题】:Angular + rxjs: No provider for SubscriptionAngular + rxjs:没有订阅提供者
【发布时间】:2018-03-10 04:28:34
【问题描述】:

当服务持有一个值并且组件订阅它时,我正在尝试以角度实现服务组件通信。我正在使用 rxjs 订阅,但我得到了

Uncaught (in promise): Error: No provider for Subscription!

这是我在服务中所做的:

import { Injectable } from '@angular/core';
import { Observable } from 'rxjs';
import { Subject } from 'rxjs/Subject';

@Injectable()
export class PracticeContextService {
  practice: Subject<any> = new Subject<any>();
  public practiceSelected$ = this.practice.asObservable();

 setPractice(providerId: string) {
   this.practice.next({ providerId: providerId });
 }

 getPractice(): Observable<any> {
   return this.practice.asObservable();
 }
}

在组件中:

import { Component, OnDestroy, OnInit } from '@angular/core';
import { Subscription } from 'rxjs/Subscription';
import { PracticeContextService } from '../practice-context.service';

@Component({
  selector : 'practice-context-selector',
  templateUrl : './practice-context-selector.component.html',
  styleUrls : ['./practice-context-selector.component.css']
})

export class PracticeContextSelectorComponent implements OnInit, OnDestroy {

  practice: string;

  constructor(private context: PracticeContextService,
          private subscription: Subscription) {}

  ngOnInit() {
    this.subscription = this.context.practiceSelected$.subscribe(
      practice => {
        this.practice = practice;
      });
  }

  ngOnDestroy() {
    this.subscription.unsubscribe();
  }
}

组件和服务被捆绑到模块中,然后注入到另一个模块中。

import { NgModule }           from '@angular/core';
import { CommonModule }       from '@angular/common';

import { PracticeContextSelectorComponent } from './practice-context-selector/practice-context-selector.component';
import { PracticeContextService } from './practice-context.service';

@NgModule({
  imports : [
    CommonModule
  ],
  declarations : [
    PracticeContextSelectorComponent
  ],
  providers : [
    PracticeContextService,
  ],
  exports: [
    PracticeContextSelectorComponent
  ]
})

export class PracticeContextModule {}

显然,我在这里做错了

【问题讨论】:

  • 如果你在一个由 Angulars DI 实例化的类中有一个构造函数参数,那么必须有一个匹配的提供者。 constructor(private context: PracticeContextService, private subscription: Subscription)中这个参数的作用是什么?
  • 订阅不适用于DI,像import { Subscription} from 'rxjs/Subscription';一样导入。
  • @lyubimov-roman 我实际上是在组件中进行此导入。如果我不必将此依赖项连接到构造函数中的组件,那么正确的使用方法是什么?我在问,因为我发现了一些使用这种方法的例子,但它似乎对我不起作用。
  • 为什么要在构造函数中导入,它的目的是什么?

标签: angular typescript rxjs


【解决方案1】:

只需从构造函数中删除private subscription: Subscription 并将其放入类的属性中。

【讨论】:

    【解决方案2】:

    在您的服务中,您可以首先像这样更改 rxjs 导入:

    import { Observable, Subscription } from 'rxjs/Rx';
    

    我在从 'rxjs/Observable' 导入 { Observable } 时遇到了问题。现在我很小心这个:P! (我也许应该进一步挖掘以找出幕后真正发生的事情。)

    那么,正如 Lyubimov Roman 在上面的评论中所说,你不应该通过构造函数导入 rxjs subscription。我不明白你对柳比莫夫评论的回答。您能否向我们提供您提到的示例,以便我们弄清楚您的意图是什么?

    如果您需要在组件中使用 subscription 对象,只需像这样导入它:

    import { Subscription } from 'rxjs/Rx';
    

    【讨论】:

    • 如果不想导入整个模块,最好单独导入。
    • 确实,我终于意识到我可以在声明类型的部分声明它,比如subscription: Subscription;而不是构造函数。谢谢!
    • 哈!我确切地知道@vitalym 发生了什么,因为我只是做了完全相同的事情。我打算在构造函数上方声明我的订阅,但所有 private 声明看起来都一样!大声笑
    【解决方案3】:

    从构造函数中删除它并在外面声明它。

    private _Subscription: Subscription;
    
      constructor() {
      }
    

    【讨论】:

      【解决方案4】:

      即使我是 Angular 新手并且多次遇到这个问题并且无法理解问题是什么。因此,首先要确保将导入正确声明为 import { Observable, Subscription } from 'rxjs';

      对我来说,错误是 空注入错误。没有订阅提供者

      最初,我开始在构造函数中将 Subscription 声明为:

      constructor(){private activatedsubscription:Subscription}
      

      这行不通,因为我后来意识到它是空注入的原因是因为它是在构造函数内部声明的,而它应该在构造函数外部声明为属性或在类中全局声明为:

      export class Component implements OnInit{
      activatedsubscription:Subscription
      }
      

      注意:确保在调用 OnDestroy 销毁组件时取消订阅订阅。否则你会有内存泄漏

      【讨论】:

      • 干得好,谢谢你救了我 :),是的,必须使用 OnDestroy
      【解决方案5】:

      我一开始要确保您将导入正确声明为

      import { Subscription } from 'rxjs'
      

      然后我用它作为

      public subscription : Subscription = new Subscription();
      

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2021-12-30
        • 1970-01-01
        • 2021-12-19
        • 1970-01-01
        • 2021-11-18
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多