【问题标题】:TestBed mocking serviceTestBed 模拟服务
【发布时间】:2018-08-15 12:07:39
【问题描述】:

我用方法测试组件:

     switchDocumentLanguage(lang, formData):any {
        if (lang === this.currentLang) {
          return null;
        }
        if (formData.invalid && this.currentLang === this.appConfig.defaultLanguage ||
          !this.documentFormData.content && this.currentLang === this.appConfig.defaultLanguage) {

          return this.modalService.open(this.setDefaultModal);

        }

        //(2*)
        if (formData.invalid || !this.documentFormData['content']) {
          return this.modalService.open(this.tabSwitchModal).result.then(() => {
            this.fillFormData(lang);
          }, (reason) => {
          });
        } else {
          return this.fillFormData(lang);
        }
      }

它属于标记为 (2*) 的条件

在测试中我使用存根类 ModalService:

    class ModalService {
      open(someArg?: any){
        return {result : Promise.resolve('success')};
      }
    }

    const appConfig =
    {
      defaultLanguage: 'en-US'
    }

我的测试配置如下:

 describe('document.edit component test', () => {

  let component: DocumentEditComponent;
  let fixture: ComponentFixture<DocumentEditComponent>;

  beforeEach(() => {

    TestBed.configureTestingModule({
      imports: [FormsModule],

      schemas: [NO_ERRORS_SCHEMA],
      declarations: [DocumentEditComponent],
      providers: [{provide: AppConfig, useValue: appConfig},
        {provide: DocumentsService, useValue: documentsService},
        {provide: NgbModal, useClass: ModalService},
        {provide: ActivatedRoute, useValue: activatedRoute},
        {provide: BaThemeSpinner, useValue: loader},
        {provide: PopupResultService, useValue: popupResultService},
      ],
    })
  });

  beforeEach(() => {
    fixture = TestBed.createComponent(DocumentEditComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
  });

这是给我错误的测试:

  it("try to leave custom language with invalid form", async(() => {
      const componentService = fixture.debugElement.injector.get(NgbModal);

      let spyObj = spyOn(componentService, "open")

      component.documentFormData.content = "some test values";
      component.currentLang = "es-VE";


      fixture.detectChanges();
      component.switchDocumentLanguage("ru-Ru", {invalid: true})
      fixture.detectChanges();

      fixture.whenStable().then(() => {
        fixture.detectChanges();
        expect(spyObj).toHaveBeenCalled()
      })
    }));

错误文字:

document.edit component test try to leave custom language with invalid form
Failed: Cannot read property 'result' of undefined
TypeError: Cannot read property 'result' of undefined

看起来我的存根类“ModalService”没有返回任何内容,我试图将 console.log() 放在那里,但它从未出现。 有人遇到过类似的吗?

【问题讨论】:

    标签: angular jasmine testbed


    【解决方案1】:

    它没有被调用,因为你有一个间谍。

    可能你可以做的是,用callThrough()扩展间谍

    let spyObj = spyOn(componentService, "open").and.callThrough();
    

    编辑:

    你也可以使用returnValue()

    let spyObj = spyOn(componentService, "open").and.returnValue({result : Promise.resolve('success')}); 
    

    在这种情况下,open() 不会被调用,而是您将返回与模拟类方法返回的相同结果。如果你使用它,你也不需要模拟类。

    【讨论】:

    • 但我需要知道它是由组件调用的。如果我监视 smth,它永远不会被组件调用?
    • 我遇到了其他情况:it("try to leave custom language with invalid form", async(() => { const componentService = fixture.debugElement.injector.get(NgbModal); let spyObj = spyOn(componentService, "open") component.switchDocumentLanguage("ru-Ru", {invalid: true}) fixture.detectChanges(); fixture.whenStable().then(() => { fixture.detectChanges(); 期望(spyObj).toHaveBeenCalled() }) }));
    • 它转到“switchDocumentLanguage”第二个“if”,其中没有调用模拟服务“open”方法的“result”,它工作正常,它检测到 Spyed 对象。
    • 如果你不将and.callThrough()添加到spy,那么open()将不会被调用。您可以验证差异。
    • 好吧,您也可以使用let spyObj = spyOn(componentService, "open").and.returnValue({result : Promise.resolve('success')});。在这种情况下,open() 不会被调用,而是会返回与模拟类方法返回的结果相同的结果。
    猜你喜欢
    • 2018-02-01
    • 2018-11-21
    • 2016-12-19
    • 1970-01-01
    • 2018-04-10
    • 2017-10-31
    • 2021-05-14
    • 2018-08-04
    • 2011-02-10
    相关资源
    最近更新 更多