#typescript #jestjs #mocking #ts-jest #testing-library
#машинописный текст #jestjs #осмеяние #тс-шутка #тестирование-библиотека
Вопрос:
Результаты продолжают меняться, когда я провожу тест на пряжу.
это имя ошибки «Запрос не выполнен с кодом состояния 400»
но я уже знаю, что функция запроса Api уже издевается
подобный этому
import * as api from '@api/user'; jest.mock('@api/user'); (api.fetchApiKeyUpdate as jest.Mock).mockImplementationOnce(() =gt; { throw { response: { data: { code: 'EX_INVALID_APIKEY_2015' } } }; }); (api.fetchApiKeyUpdate as jest.Mock).mockImplementationOnce(() =gt; ({ status: 'success', user: { id: '99b1231230', country: 'KR', language: 'ko', }, }));
Испытание, проведенное на этом, проходит. Но тесты часто проваливаются. Интересно, что я должен подозревать?
export const fetchApiKeyUpdate = async ({ exchange, apiKey, secretKey, passphrase, otpCode, }: ApiKeyUpdateRequest): Promiselt;UserInfoUpdateResponse | ApiAuthResponsegt; =gt; { const { data } = await axios.post( apiKeyUpdateUrl, { apiKey, secretKey, passphrase, otpCode }, { headers: { exchange } }, ); return data; };
Внизу находится часть кода, который я изменил.
jest.mock('@api/user'); describe('API Register Success', () =gt; { const mockResponse = { status: 'success', user: { id: '99bd10e123400', userName: 't123st07', receiveMarketingInfo: true, }, }; beforeEach(() =gt; { (api.fetchApiKeyUpdate as jest.Mock).mockResolvedValueOnce(mockResponse); }); it('키인증 성공시 아이콘 변경', async () =gt; { const { container } = render( lt;ApiRegistrationBinanceTab isOpen handleOpenTab={jest.fn()} /gt;, ); userEvent.type(screen.getByPlaceholderText(/api key/i), 'apikey'); userEvent.click(screen.getByRole('button', { name: /Verify/i })); await waitFor(() =gt; { expect(container.querySelector('#certified-icon')).toBeTruthy(); }); }); }); describe('API Register Fail', () =gt; { const mockResponse = { response: { data: { code: 'EX_INVALID_APIKEY_2015' } } }; beforeEach(() =gt; { (api.fetchApiKeyUpdate as jest.Mock).mockRejectedValueOnce(mockResponse); }); it('remove input value if error code EX_INVALID_APIKEY_2015 or API_MANAGEMENT_ALREADY_REGISTERED', async () =gt; { render( lt;ApiRegistrationBinanceTab isOpen handleOpenTab={jest.fn()} /gt;, ); userEvent.type(screen.getByPlaceholderText(/api key/i), 'apikey'); userEvent.click(screen.getByRole('button', { name: /Verify/i })); await waitFor(() =gt; { expect(screen.getByPlaceholderText(/api key/i)).toHaveValue(''); }); }); });
FAIL src/components/articles/modal/custom/forgotPassword/ForgotPassword.spec.tsx ● 비밀번호 변경 스텝별로 진행 Request failed with status code 400 at createError (node_modules/axios/lib/core/createError.js:16:15) at settle (node_modules/axios/lib/core/settle.js:17:12) at XMLHttpRequest.handleLoad (node_modules/axios/lib/adapters/xhr.js:62:7) at XMLHttpRequest.lt;anonymousgt; (node_modules/jsdom/lib/jsdom/living/helpers/create-event-accessor.js:32:32) at innerInvokeEventListeners ...
я подаю заявку перед началом и изменяю mockimplementationOnce gt; mockResolvedValueOnce, mockRejectedValueOnce
Но проблема в том, что сбой появляется периодически по мере изменения страниц(теста).
Что мне интересно в сообщении об ошибке… я высмеял функцию(например, fetchAuthMail.. fetchApiKeyUpdate) в запросе.
Поэтому я не знаю, почему сообщение об ошибке исходит от axios, хотя я не думаю, что на самом деле отправил запрос в тест.
Комментарии:
1. Как вы его использовали
api.fetchApiKeyUpdate
?2. Событие пользователя. введите(screen.getByPlaceholderText(/введите пароль/i), «пароль»); событие пользователя.нажмите(screen.getByRole(«кнопка», { имя: /Проверить/i })); gt;gt;gt;fetchapikeyupdate
3. ожидание waitFor (() = gt; { ожидание(screen.getByPlaceholderText(/ключ api/i)). toHaveValue(«); });
4. когда-нибудь все тесты пройдут с предупреждением UnhandledPromiseRejectionWarning: Ошибка: Запрос не удался с кодом состояния 400, UnhandledPromiseRejectionWarning: Необработанное обещание отклонено
Ответ №1:
Вы не должны использовать mockImplementation
, потому что функция возвращает обещание. Просто используйте mockResolvedValue
и mockRejectedValue
заставьте его вернуть Обещание.
Кроме того, вы должны разделить насмешки с некоторыми describe
(по одному для каждого варианта использования) и добавить насмешки в beforeAll
/ beforeEach
функции.
Лично я только что протестировал его, я сохранил ваш @api/user.ts (я только что добавил axios
импорт), и с помощью этих файлов он работал (работал на 100%, никогда не подводил). :
индекс.ts
import * as api from '@api/user'; export const main = async () =gt; { const response = await api.fetchApiKeyUpdate({ exchange: 'fake-exchange', apiKey: 'fake-apiKey', secretKey: 'fake-secretKey', passphrase: 'fake-passphrase', otpCode: 'fake-otpCode', }); return response.user; };
index.spec.ts
import { main } from './index'; import * as api from '@api/user'; jest.mock('@api/user'); jest.mock('axios', () =gt; ({ post: jest.fn().mockImplementation(() =gt; { console.error('axios should be mocked !'); // If some logs are shown, it means that one axios request was not mocked. }), })); describe('UT main tests', () =gt; { describe('error', () =gt; { beforeEach(() =gt; { (api.fetchApiKeyUpdate as jest.Mock).mockRejectedValue({ response: { data: { code: 'EX_INVALID_APIKEY_2015' } } }); }); it('should rejects but not throw', async () =gt; { // Note that if you want to use .toThrow() method, you should set in mockRejectedValue an Error await expect(main()).rejects.toStrictEqual({ response: { data: { code: 'EX_INVALID_APIKEY_2015' } } }); }); }); describe('error thrown', () =gt; { beforeEach(() =gt; { (api.fetchApiKeyUpdate as jest.Mock).mockRejectedValue(Error('FAKE ERROR')); }); it('should rejects and throw', async () =gt; { // All working await expect(main()).rejects.toThrow(Error); await expect(main()).rejects.toThrowError('FAKE ERROR'); await expect(main()).rejects.toThrowError(Error('FAKE ERROR')); }); }); describe('success', () =gt; { const mockResponse = { status: 'success', user: { id: '99b1231230', country: 'KR', language: 'ko', }, }; beforeEach(() =gt; { (api.fetchApiKeyUpdate as jest.Mock).mockResolvedValue(mockResponse); }); it('should return user', async () =gt; { const response = await main(); expect(response).toStrictEqual(mockResponse.user); }); }); });
РЕДАКТИРОВАТЬ : Я добавил макет сообщения axios напрямую, вы должны проверить, появляется ли журнал ошибок на вашей консоли. Если это так, это означает, что вы забыли посмеяться над некоторыми вызовами axios.
Комментарии:
1. эта структура выглядит хорошо, поэтому я применил ее.
2. Но проблема, с которой я столкнулся, все еще существует.
3. Я отредактировал сообщение, которое вы можете проверить
4. Я занимался шпионажем в другом месте, так что фактический запрос поступал в одном месте. Но ошибка продолжала появляться на другой странице, поэтому я не мог ее найти. Ваш ответ очень помог мне в написании тестового кода. Спасибо~