【问题标题】:TypeError: Cannot read properties of undefined (reading 'subscribe') in JasmineTypeError:无法读取 Jasmine 中未定义(读取“订阅”)的属性
【发布时间】:2021-11-16 12:35:23
【问题描述】:

我正在尝试为以下方法编写测试用例:-

 subscriptionPackages() {
    this.managePackageService.getPackages().subscribe(
      (response) => {
        this.packagePlan = response;
      },
      (httpErrorRes) => {
      }
    );
  }

我已经在我的 spec.ts 文件中尝试了下面的 sn-p 来覆盖上面的代码:-

  fdescribe('AddProductComponent', () => {
  let component: AddProductComponent;
  let fixture: ComponentFixture<AddProductComponent>;
  let packageServiceStub = jasmine.createSpyObj('ManagePackageService', ['getPackages']);

  beforeEach(async () => {
    await TestBed.configureTestingModule({
      imports: [HttpClientTestingModule,ReactiveFormsModule,FormsModule,ToastrModule.forRoot(),
        TranslateModule.forRoot(), NgSelectModule],
      declarations: [ AddProductComponent ],
      providers :[AppConfig,
        { provide: ManagePackageService, useValue: packageServiceStub }]
    })
    .compileComponents();
  });

  beforeEach(() => {
    fixture = TestBed.createComponent(AddProductComponent);
    component = fixture.componentInstance;
    component.packagePlan = [{'name':'basic', 'id':1}, {'name':'advance', 'id':2}, {'name':'premium', 'id':3}];
    fixture.detectChanges();
  });

it('should create  subscriptionPackages', () => {
  const mockpackageResponse = []; 
  packageServiceStub.getPackages.and.returnValue(of(mockpackageResponse));
  component.subscriptionPackages();
  expect(component.packagePlan).toBeTruthy();
 });

从这段代码中我的测试用例被覆盖,但我得到以下错误:-

【问题讨论】:

    标签: jasmine karma-runner


    【解决方案1】:

    你是在组件的ngOnInit还是constructor中调用subscriptionPackages

    如果您在ngOnInit 中调用它,则需要在第一个fixture.detectChanges() 之前模拟returnValue。第一个fixture.detectChanges() 是在调用ngOnInit 时。

    beforeEach(() => {
        fixture = TestBed.createComponent(AddProductComponent);
        component = fixture.componentInstance;
        // !! Move this line here if calling subscriptionPackages in ngOnInit !!
        packageServiceStub.getPackages.and.returnValue(of(mockpackageResponse));
        component.packagePlan = [{'name':'basic', 'id':1}, {'name':'advance', 'id':2}, {'name':'premium', 'id':3}];
        fixture.detectChanges();
      });
    
    it('should create  subscriptionPackages', () => {
      const mockpackageResponse = []; 
      component.subscriptionPackages();
      expect(component.packagePlan).toBeTruthy();
     });
    
    beforeEach(() => {
         // !! Move this line here if calling subscriptionPackages in constructor !!
        packageServiceStub.getPackages.and.returnValue(of(mockpackageResponse));
        fixture = TestBed.createComponent(AddProductComponent);
        component = fixture.componentInstance;
        component.packagePlan = [{'name':'basic', 'id':1}, {'name':'advance', 'id':2}, {'name':'premium', 'id':3}];
        fixture.detectChanges();
      });
    
    it('should create  subscriptionPackages', () => {
      const mockpackageResponse = []; 
      component.subscriptionPackages();
      expect(component.packagePlan).toBeTruthy();
     });
    

    【讨论】:

    • 谢谢,现在已经解决了。
    • 如果我们在 ngOnChanges 中调用方法,这是否也适用于这种情况,就像我为 'subscriptionPackage()' 所做的那样,如果相同的方法 ngOnChange
    • ngOnChanges 仅在 @Input 属性从父组件更改时运行。如果您不想将组件托管在父组件中,您可以手动调用ngOnChanges。看看这篇文章:medium.com/@christophkrautz/….
    • 我刚刚发布了这篇文章,请查看下面的链接,如果您对此有任何想法,请向我提出解决方案。 stackoverflow.com/questions/70000998/…
    • 我发现任何订阅都最好在 OnChange 事件上完成,并保持 ngOnInit 尽可能简单可以解决这个问题 - 谢谢
    猜你喜欢
    • 1970-01-01
    • 2019-07-19
    • 2018-02-13
    • 2021-11-23
    • 2020-06-17
    • 2020-08-05
    • 1970-01-01
    • 1970-01-01
    • 2020-05-26
    相关资源
    最近更新 更多