Error: <toHaveBeenCalled> : Expected a spy, but got Function in Jamsine
Error: <toHaveBeenCalled> : Expected a spy, but got Function in Jamsine
我是 Angular 中使用 Jasmine 和 Karma 进行单元测试的新手。我写了一个 spec 文件,但出现错误。让我先展示一下我到目前为止所做的事情。我创建了一个自定义组件:
TimeselectorComponent
startRange = moment('12-01-01');
endRange = moment ('12-12-01');
modes= ['Calendar Year', 'Year-to-date', 'Rolling Year', 'Custom'];
date = new Date();
currentYear = this.date.getFullYear(); // or simply currentYear = 2020;
@ViewChild('primaryMonthPicker') primaryMonthPicker: MonthpickerComponent; // a child component
primaryDropDown(startRange, endRange) {
if (this.primaryMode === this.modes[0]) {
this.initCalendarYear(this.primaryMonthPicker, this.currentYear);
} else if (this.primaryMode === this.modes[1]) {
this.initYearToDate(this.primaryMonthPicker, this.currentYear);
} else if (this.primaryMode === this.modes[2]) {
this.initRollingYear(this.primaryMonthPicker, this.currentYear);
}
}
在上面的代码中 MonthpickerComponent
是另一个自定义组件,它是 TimeselectorComponent
的唯一子组件。
我只想检查 primaryDropDown
何时被调用,然后 initCalendarYear
也应该被调用。这是规范文件:
import { TestBed, ComponentFixture, async } from '@angular/core/testing';
import { TimeselectorComponent } from './timeselector.component';
...
describe('TimeselectorComponent', () => {
let fixture: ComponentFixture<TimeselectorComponent>;
@Component({
selector: 'app-monthpicker',
template: '<div></div>'
})
class FakeMonthpickerComponent {
// methods of MonthpickerComponent
}
let MODES = [];
beforeEach(async(() => {
MODES = ['Calendar Year', 'Year-to-date', 'Rolling Year', 'Custom'];
TestBed.configureTestingModule({
declarations: [FakeMonthpickerComponent, TimeselectorComponent],
schemas: [NO_ERRORS_SCHEMA]
}).compileComponents();
}));
beforeEach(() => {
fixture = TestBed.createComponent(TimeselectorComponent);
});
// other test cases that are passing
// need help with this test case
it('should call initCalendarYear when primaryDropDown is called', () => {
const startRange=moment('2020-01-01');
const endRange= moment('2020-12-01');
spyOn(fixture.componentInstance, 'initCalendarYear');
fixture.componentInstance.primaryMode=MODES[0];
fixture.componentInstance.primaryDropDown(startRange, endRange);
expect(fixture.componentInstance.initCalendarYear).toHaveBeenCalled();
});
});
但是我收到了这个错误:
我必须测试是否为关联的 if-else
语句调用了正确的方法。请帮助我。
这是 stackblitz。
import { TestBed, ComponentFixture, async } from '@angular/core/testing';
import { TimeselectorComponent } from './timeselector.component';
import { Component, NO_ERRORS_SCHEMA } from '@angular/core';
var moment = require('moment/moment')
describe('TimeselectorComponent', () => {
let fixture: ComponentFixture<TimeselectorComponent>;
@Component({
selector: 'app-monthpicker',
template: '<div></div>'
})
class FakeMonthpickerComponent {
// methods of MonthpickerComponent
}
let MODES = [];
beforeEach(async(() => {
MODES = ['Calendar Year', 'Year-to-date', 'Rolling Year', 'Custom'];
TestBed.configureTestingModule({
declarations: [FakeMonthpickerComponent, TimeselectorComponent],
schemas: [NO_ERRORS_SCHEMA]
}).compileComponents();
}));
beforeEach(() => {
fixture = TestBed.createComponent(TimeselectorComponent);
});
// other test cases that are passing
// need help with this test case
it('should call initCalendarYear when primaryDropDown is called', () => {
const startRange=moment('2020-01-01');
const endRange= moment('2020-12-01');
spyOn(fixture.componentInstance, 'initCalendarYear');
fixture.componentInstance.primaryMode=MODES[0];
fixture.componentInstance.primaryDropDown(startRange, endRange);
expect(fixture.componentInstance.initCalendarYear).toHaveBeenCalled();
});
});
以上游戏我成功了:-
像这样添加间谍
spyOn(fixture.componentInstance, 'initCalendarYear');
以此更改最后一行
expect(fixture.componentInstance.initCalendarYear).toHaveBeenCalled();
所以你的最终测试用例应该是这样的
it('should call initCalendarYear when primaryDropDown is called', () => {
const startRange=moment('2020-01-01');
const endRange= moment('2020-12-01');
fixture.componentInstance.primaryMode = MODES[0];
spyOn(fixture.componentInstance, 'initCalendarYear');
fixture.componentInstance.primaryDropDown(startRange, endRange);
expect(fixture.componentInstance.initCalendarYear).toHaveBeenCalled();
});
我是 Angular 中使用 Jasmine 和 Karma 进行单元测试的新手。我写了一个 spec 文件,但出现错误。让我先展示一下我到目前为止所做的事情。我创建了一个自定义组件:
TimeselectorComponent
startRange = moment('12-01-01');
endRange = moment ('12-12-01');
modes= ['Calendar Year', 'Year-to-date', 'Rolling Year', 'Custom'];
date = new Date();
currentYear = this.date.getFullYear(); // or simply currentYear = 2020;
@ViewChild('primaryMonthPicker') primaryMonthPicker: MonthpickerComponent; // a child component
primaryDropDown(startRange, endRange) {
if (this.primaryMode === this.modes[0]) {
this.initCalendarYear(this.primaryMonthPicker, this.currentYear);
} else if (this.primaryMode === this.modes[1]) {
this.initYearToDate(this.primaryMonthPicker, this.currentYear);
} else if (this.primaryMode === this.modes[2]) {
this.initRollingYear(this.primaryMonthPicker, this.currentYear);
}
}
在上面的代码中 MonthpickerComponent
是另一个自定义组件,它是 TimeselectorComponent
的唯一子组件。
我只想检查 primaryDropDown
何时被调用,然后 initCalendarYear
也应该被调用。这是规范文件:
import { TestBed, ComponentFixture, async } from '@angular/core/testing';
import { TimeselectorComponent } from './timeselector.component';
...
describe('TimeselectorComponent', () => {
let fixture: ComponentFixture<TimeselectorComponent>;
@Component({
selector: 'app-monthpicker',
template: '<div></div>'
})
class FakeMonthpickerComponent {
// methods of MonthpickerComponent
}
let MODES = [];
beforeEach(async(() => {
MODES = ['Calendar Year', 'Year-to-date', 'Rolling Year', 'Custom'];
TestBed.configureTestingModule({
declarations: [FakeMonthpickerComponent, TimeselectorComponent],
schemas: [NO_ERRORS_SCHEMA]
}).compileComponents();
}));
beforeEach(() => {
fixture = TestBed.createComponent(TimeselectorComponent);
});
// other test cases that are passing
// need help with this test case
it('should call initCalendarYear when primaryDropDown is called', () => {
const startRange=moment('2020-01-01');
const endRange= moment('2020-12-01');
spyOn(fixture.componentInstance, 'initCalendarYear');
fixture.componentInstance.primaryMode=MODES[0];
fixture.componentInstance.primaryDropDown(startRange, endRange);
expect(fixture.componentInstance.initCalendarYear).toHaveBeenCalled();
});
});
但是我收到了这个错误:
我必须测试是否为关联的 if-else
语句调用了正确的方法。请帮助我。
这是 stackblitz。
import { TestBed, ComponentFixture, async } from '@angular/core/testing';
import { TimeselectorComponent } from './timeselector.component';
import { Component, NO_ERRORS_SCHEMA } from '@angular/core';
var moment = require('moment/moment')
describe('TimeselectorComponent', () => {
let fixture: ComponentFixture<TimeselectorComponent>;
@Component({
selector: 'app-monthpicker',
template: '<div></div>'
})
class FakeMonthpickerComponent {
// methods of MonthpickerComponent
}
let MODES = [];
beforeEach(async(() => {
MODES = ['Calendar Year', 'Year-to-date', 'Rolling Year', 'Custom'];
TestBed.configureTestingModule({
declarations: [FakeMonthpickerComponent, TimeselectorComponent],
schemas: [NO_ERRORS_SCHEMA]
}).compileComponents();
}));
beforeEach(() => {
fixture = TestBed.createComponent(TimeselectorComponent);
});
// other test cases that are passing
// need help with this test case
it('should call initCalendarYear when primaryDropDown is called', () => {
const startRange=moment('2020-01-01');
const endRange= moment('2020-12-01');
spyOn(fixture.componentInstance, 'initCalendarYear');
fixture.componentInstance.primaryMode=MODES[0];
fixture.componentInstance.primaryDropDown(startRange, endRange);
expect(fixture.componentInstance.initCalendarYear).toHaveBeenCalled();
});
});
以上游戏我成功了:-
像这样添加间谍
spyOn(fixture.componentInstance, 'initCalendarYear');
以此更改最后一行
expect(fixture.componentInstance.initCalendarYear).toHaveBeenCalled();
所以你的最终测试用例应该是这样的
it('should call initCalendarYear when primaryDropDown is called', () => {
const startRange=moment('2020-01-01');
const endRange= moment('2020-12-01');
fixture.componentInstance.primaryMode = MODES[0];
spyOn(fixture.componentInstance, 'initCalendarYear');
fixture.componentInstance.primaryDropDown(startRange, endRange);
expect(fixture.componentInstance.initCalendarYear).toHaveBeenCalled();
});