首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >角9单元测试:如何模拟测试组件的导入?

角9单元测试:如何模拟测试组件的导入?
EN

Stack Overflow用户
提问于 2020-10-08 10:57:27
回答 1查看 1.6K关注 0票数 1

因此,我目前正在为一个角9组件编写一个Jasmine/Karma单元测试。

我的应用程序是如何工作的:我用D3编写了一个小的D3,它在漏斗状图中显示给定的数据。然后,我编写了一个包含这个FunnelComponentFunnel,并在实际图表旁边显示了一些元信息。

这是我要测试的组件:

funnel.component.ts

代码语言:javascript
复制
import { Component } from '@angular/core';
import { Funnel } from './d3charts/funnel.ts';
import { FunnelData } from './funnel.data';

@Component({
  selector: 'v7-funnel-component',
  templateUrl: './funnel.html'
})
export class FunnelComponent {

  private funnel: Funnel = null;

  constructor() {}

  public createFunnel(funnelData: FunnelData): void {
      this.funnel = new Funnel();
      this.funnel.setData(funnelData);
      this.funnel.draw();
  }
}

这是我的业力-茉莉花单元-测试该组件:

funnel.component.spec.ts

代码语言:javascript
复制
import { TestBed, ComponentFixture } from '@angular/core/testing';
import { } from 'jasmine';
import { FunnelComponent } from './funnel.component';
import { Component } from '@angular/core';
import { FunnelData } from './funnel.data';
import { Funnel } from './d3charts/funnel.ts';

@Component({selector: 'funnel', template: ''})
class FunnelStub {
  private data: FunnelData = null;

  public setData(data: FunnelData): void
  {this.data = data;}
  {}
  public draw(): void
  {}
  public update(funnelData: FunnelData): void
  {}
}

/**
 * Testing class for FunnelComponent.
 */
describe('Component: Funnel', () => {

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

  beforeEach(async(() => {
    TestBed
    .configureTestingModule({
      declarations: [
        FunnelComponent,
        FunnelStub
      ],
      providers: [
        { provide: Funnel, useValue: FunnelStub}
      ]
    })
    .compileComponents()
    .then(() => {
      fixture = TestBed.createComponent(FunnelComponent);
      component = fixture.componentInstance;
    });
  }));

it('#createFunnel should set data of funnel. Filled data should set filled funnel.', () => {
    expect(component["funnel"]).toBeNull();

    let exampleFunnelData = new FunnelData("testcaption", "testdescription", 8);
    component.createFunnel(exampleFunnelData);

    expect(component["funnel"]).toBeDefined();
    expect(component["funnel"]["data"]).toBeDefined();
    expect(component.data.caption).toEqual("testcaption");
    expect(component.data.description).toEqual("testsubtext");
    expect(component.data.value).toEqual(8);
  });
});

我想在这里测试createFunnel方法。但我不希望我的createFunnel方法将真正的Funnel分配给this.funnel,而是使用FunnelStub。知道怎么做吗?

{ provide: Funnel, useValue: FunnelStub}添加到提供程序数组没有帮助:(

向你问好,塞巴斯蒂安

EN

回答 1

Stack Overflow用户

回答已采纳

发布于 2020-10-08 11:39:39

这不起作用,因为漏斗不是提供者:

代码语言:javascript
复制
providers: [
  { provide: Funnel, useValue: FunnelStub}
]

对测试最有帮助的是为漏斗的创建创建一个服务。

代码语言:javascript
复制
export abstract class FunnelProvider {
  abstract createFunnel(): Funnel;
}

然后,该服务可以有两个实现,一个在应用程序中使用,一个在测试中使用。

代码语言:javascript
复制
@Injectable()
export class DefaultFunnelProvider {
  createFunnel() {
    return new Funnel(); // Return real funnel object.
  }
}
代码语言:javascript
复制
@Injectable()
export class MockFunnelProvider {
  createFunnel() {
     // Return stub funnel. Assuming that they share the same interface.
    return new FunnelStub() as Funnel;
  }
}

现在,您必须在DefaultFunnelProvider中定义FunnelModule (声明FunnelComponent的模块):

代码语言:javascript
复制
@NgModule({
  ... // other stuff
  providers: [{provide: FunnelProvider, useClass: DefaultFunnelProvider}]
})
export class FunnelModule {}

然后将FunnelProvider注入到FunnelComponent中,并使用它创建漏斗:

代码语言:javascript
复制
export class FunnelComponent {

  private funnel: Funnel = null;

  constructor(private funnelProvider: FunnelProvider) {}

  public createFunnel(funnelData: FunnelData): void {
      this.funnel = this.funnelProvider.createFunnel();
      this.funnel.setData(funnelData);
      this.funnel.draw();
  }
}

虽然做了很多工作,但现在最酷的是您可以将FunnelProvider的Mock实现插入到TestBed中:

代码语言:javascript
复制
TestBed
    .configureTestingModule({
      declarations: [
        FunnelComponent,
        FunnelStub
      ],
      providers: [
        { provide: FunnelProvider, useValue: MockFunnelProvider }
      ]
    })

现在,当调用funnelProvider.createFunnel时,它不会返回真正的漏斗,而是返回漏斗存根。

如果在测试期间必须这样做,您可以将组件漏斗字段转换为FunnelStub (例如,如果它有一些特殊的方法):

代码语言:javascript
复制
const funnelStub = component.funnel as FunnelStub;
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/64261091

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档