我想为utils方法编写测试。在那种方法中,我通过id获取一个html元素,然后更改该元素的颜色。问题在于该元素仅在单击按钮后可用。如何模拟元素?
UtilListItem.js
import variables from '../stylesheets/Variables.scss';
export function activeListItem(props){
let listItem = document.getElementById(props.id);
listItem.style.backgroundColor = variables.whiteGray;
return listItem;
}
UtilListeItem.test.js
it('check if the correct color is set for the acitve list item', () => {
let props = {id:'123'}
const listItem = activeListItem(props);
expect(listItem.style.backgroundColor).toBe('#ededed');
});
错误
TypeError: Cannot read property 'style' of null
答案 0 :(得分:0)
此行有问题:
let listItem = document.getElementById(props.id);
首先创建一个元素以进行嘲笑。请务必等待文档并注入。
在这种情况下,您正在做的事情是获取尚待测试/不存在的元素。
---编辑以添加示例---
需要添加的内容: https://jestjs.io/docs/en/configuration#setupfiles-array
其他人通过示例解决方案对类似问题做出了回应: https://stackoverflow.com/a/41186342/5768332
答案 1 :(得分:0)
我可以想到两种选择,您可以选择其中一种:
对功能activeListItem的listItem进行检查
export function activeListItem(props) {
let listItem = document.getElementById(props.id);
if (listItem === null) {
return;
}
listItem.style.backgroundColor = variables.whiteGray;
return listItem;
}
在测试用例中添加虚拟元素
it('check if the correct color is set for the acitve list item', () => {
/** Create and add dummy div **/
let testId = "dummy-testId";
let newDiv = document.createElement("div");
newDiv.setAttribute("id", testId);
document.body.appendChild(newDiv);
let props = {id: testId}
const listItem = activeListItem(props);
expect(listItem.style.backgroundColor).toBe('#ededed');
});
答案 2 :(得分:0)
我会建议您jest.spyOn。这是监视功能和/或附加某些模拟行为的一种非常方便的方法。
您可以像这样使用它:
imoprt { activeListItem } from './utils';
let spy;
beforeAll(() => {
spy = jest.spyOn(document, 'getElementById');
});
describe('activeListItem', () => {
describe('with found element', () => {
let mockElement;
beforeAll(() => {
// here you create the element that the document.createElement will return
// it might be even without an id
mockElement = document.createElement(....);
spy.mockReturnValue(mockElement);
});
// and then you could expect it to have the background
it('should have the background applied', () => {
expect(mockElement.style.backgroundColor).toBe('#ededed');
});
});
describe('without found element', () => {
// and here you can create a scenario
// when document.createElement returns null
beforeAll(() => {
spy.mockReturnValue(null);
});
// and expect you function not to throw an error
it('should not throw an error', () => {
expect(() => activeListItem({id:'123'})).not.toThrow();
});
});
});
模拟.scss
文件也是一个好主意,因为它是实用程序文件的依赖项,因此更改时不会影响单元测试。