#javascript #reactjs #unit-testing #jestjs
#javascript #reactjs #модульное тестирование #jestjs
Вопрос:
У меня есть функция, которая вызывает функцию, которая возвращает обещание. Вот код для этого:
export const func1 = ({
contentRef,
onShareFile,
t,
trackOnShareFile,
}) => e => {
trackOnShareFile()
try {
func2(contentRef).then(url => {
onShareFile({
title: t('shareFileTitle'),
type: 'application/pdf',
url,
})
}).catch(e => {
if (process.env.NODE_ENV === 'development') {
console.error(e)
}
})
e.preventDefault()
} catch (e) {
if (process.env.NODE_ENV === 'development') {
console.error(e)
}
}
}
И func2
это вызывается func1
примерно так:
const func2 = element => {
return import('html2pdf.js').then(html2pdf => {
return html2pdf.default().set({ margin: 12 }).from(element).toPdf().output('datauristring').then(pdfAsString => {
return pdfAsString.split(',')[1]
}).then(base64String => {
return `data:application/pdf;base64,${base64String}`
})
})
}
Сейчас я пытаюсь написать несколько модульных тестов func1
, но получаю некоторые проблемы. Что я сделал до сих пор, так это:
describe('#func1', () => {
it('calls `trackOnShareFile`', () => {
// given
const props = {
trackOnShareFile: jest.fn(),
onShareFile: jest.fn(),
shareFileTitle: 'foo',
contentRef: { innerHTML: '<div>hello world</div>' },
}
const eventMock = {
preventDefault: () => {},
}
// when
func1(props)(eventMock)
// then
expect(props.trackOnShareFile).toBeCalledTimes(1)
})
it('calls `onShareFile` prop', () => {
// given
const props = {
trackOnShareFile: jest.fn(),
onShareFile: jest.fn(),
shareFileTitle: 'foo',
contentRef: { innerHTML: '<div>hello world</div>' },
}
const eventMock = {
preventDefault: () => {},
}
// when
func1(props)(eventMock)
// then
expect(props.onShareFile).toBeCalledTimes(1)
})
})
Теперь первый тест проходит, но для второго теста я получаю Expected mock function to have been called one time, but it was called zero times.
. Я не уверен, как правильно это проверить. Любая помощь приветствуется.
Комментарии:
1. Если первый проходит, а второй завершается неудачно, это означает только
func2
сбой. Если вы удалитеif (process.env.NODE_ENV === 'development') {
и зарегистрируете ошибку, вы увидите ошибку. Во время тестов ваш env, вероятноtest
, скорее, чемdevelopment
.
Ответ №1:
Хорошо, у меня это работает.
Для начала нам нужно смоделировать data-url-generator
(это то, откуда мы импортируем func2
). html2pdf
Библиотека не работает в среде тестирования, потому что она использует поддельный DOM, который не полностью реализует графику canvas.
jest.mock('./data-url-generator', () => jest.fn())
Тогда сам тест может быть написан следующим образом:
it('invokes the `onShareFile` prop', done => {
// given
const t = key => `[${key}]`
const urlMock = 'data:application/pdf;base64,PGh0bWw PGJvZHk PGRpdj5oZWxsbyB3b3JsZDwvZGl2PjwvYm9keT48L2h0bWw '
const shareFileTitle = 'bar'
const contentRef = document.createElement('div')
contentRef.textContent = 'hello world'
const trackOnShareFile = () => { }
const eventMock = {
preventDefault: () => { },
}
func2.mockResolvedValue(urlMock)
const onShareFileMock = ({ title, type, url }) => {
// then
expect(func2).toHaveBeenCalledTimes(1)
expect(func2).toHaveBeenCalledWith(contentRef)
expect(title).toBe('[shareFileTitle]')
expect(type).toBe('application/pdf')
expect(url).toBe(urlMock)
done()
}
// when
func1({
contentRef,
onShareFile: onShareFileMock,
shareFileTitle,
t,
trackOnShareFile,
})(eventMock)
})