【问题标题】:How to mock parent class method for Unit Test in Angular?如何在Angular中模拟单元测试的父类方法?
【发布时间】:2020-09-10 15:28:17
【问题描述】:

我正在为一个扩展另一个类并在运行时调用父方法的类编写单元测试。由于我不想处理父类,有什么方法可以模拟该方法调用吗?我尝试了多种方法,但没有任何效果

class A {
   doSomething(){
       console.log(123);
     }
}

class B extends A {
    work(){
      this.doSomething();
  }
}

如何在 B 类的单元测试中模拟此函数调用并返回其他内容?

我尝试了以下方法:

spyOn(b,'doSomething');

spyOn(Object.getPrototypeOf(b),'doSomething');

没有错误,只是一直调用原来的父方法

【问题讨论】:

  • 很高兴向我们展示您到目前为止到底尝试了什么以及具体错误在哪里。
  • 更新@Erbsenkoenig

标签: angular unit-testing jasmine


【解决方案1】:

您可以做的,但我不建议这样做,就是在您的 B 类中存根父方法本身。

我不推荐这种方法,因为你会在你正在单元测试的类中存根一些东西。我宁愿存根正在这个父方法中完成的事情。

但如果你真的想存根那个方法,你可以按照这些思路做一些事情:

describe('DataService', () => {
    let service: DataService;

    beforeEach(async(() => {
      TestBed.configureTestingModule({ providers: [DataService] });
    }));

    beforeEach(() => {
      service = TestBed.get(DataService); // would be inject in newer angular versions
    });

    it('test case 2', () => {
      spyOn(service as any, 'parentMethod').and.returnValue(5);
      expect(service.getData()).toEqual(5);
    });
});

DataService 在哪里


@Injectable({
  providedIn: 'root'
})
export class DataService extends AbstractDataService {
  constructor() {
    super();
   }

  getData() {
    return this.parentMethod();
  }
}

AbstractDataService

@Injectable({
  providedIn: 'root'
})
export class AbstractDataService {
  constructor() { }

  parentMethod() {
    console.log('parent method');
    return null;
  }
}

也适用于组件。但同样:不建议在被测对象内模拟方法!

describe('AppComponent', () => {
    let component: AppComponent;
    let fixture: ComponentFixture<AppComponent>;

    beforeEach(async(() => {
        TestBed.configureTestingModule({
            declarations: [AppComponent, AbstractAppComponent],
            schemas: [NO_ERRORS_SCHEMA],
            bootstrap: [AppComponent]
        }).compileComponents();
    }));

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

    it('should mock method', () => {
      spyOn(component as any, 'abstractMethod').and.returnValue(10);

      fixture.detectChanges();
      expect(component.myMethod()).toEqual(10);
    });    
});

Stackblitz with test cases for both service and component

【讨论】:

  • 是有道理的,但唯一的区别是在我的情况下它是一个组件而不是一个服务。当您尝试从组件的父类中存根方法时,这种方法不起作用。你能帮忙吗?
  • 它的工作方式相同。而不是监视服务,您将监视组件内的方法。
  • 服务 = TestBed.get(DataService);这不适用于组件。我试过 spyOn(component,'parentMethod');但它只调用原始方法
  • 当您使用 TestBed 时,您将获得您的组件实例。你可以在上面存根方法,就像在你的服务上一样
  • 看看stackblitz,我已经包含了一个组件版本。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-03-10
  • 2012-10-15
  • 2018-11-24
  • 2021-07-01
相关资源
最近更新 更多