Не удается просмотреть содержимое компонентов, отображаемых после вызова axios

#javascript #reactjs #unit-testing #axios #react-testing-library

Вопрос:

Я выполняю вызов axios в начальной визуализации моего компонента с помощью a useEffect , однако у меня возникли проблемы с фактическим тестированием содержимого моего компонента после того, как я вернул 200 ответов с содержимым этого вызова…

Компонент.jsx

 const MyComp = () => {
    const [data, setData] = useState(null);

    useEffect(() => {
        axios.get('/my-url').then(data => setData(data.data));
    }, []);

    return (
        <div>
            { data amp;amp; <div data-testid="data">{data}</div> }
        </div>
    );
}
 

Component.spec.js

 test('should render data when loaded', async () => {
    mockAxios.onGet("/my-url").reply(200, { data: 'hello' });

    rendered = render(<MyComp />);

    await waitFor(() => rendered.getByTestId("data"));

    expect(rendered.getByTestId("data")).toBeTruthy();
    expect(rendered.getByTestId("data").textContent).toBe("hello");
});
 

после выполнения этого теста я получаю сообщение об ошибке:

 Unable to find an element by: [data-testid="data"]
 

Комментарии:

1. Ты пользуешься react-testing-library ?

2. @slideshowp2 действительно, я

Ответ №1:

axios.get() возвращает AxiosResponse , который имеет интерфейс ниже:

 export interface AxiosResponse<T = any>  {
  data: T;
  status: number;
  statusText: string;
  headers: any;
  config: AxiosRequestConfig;
  request?: any;
}
 

И вы предоставляете фиктивные данные { data: 'hello' } для axios-mock-adapter . Вы должны получить hello строку через res.data.data свойство.

Напр.

Component.jsx :

 import axios from 'axios';
import React from 'react';
import { useEffect, useState } from 'react';

export const MyComp = () => {
  const [data, setData] = useState(null);

  useEffect(() => {
    axios.get('/my-url').then((res) => {
      setData(res.data.data);
    });
  }, []);

  return <div>{data amp;amp; <div data-testid="data">{data}</div>}</div>;
};
 

Component.test.jsx :

 import { MyComp } from './Component';
import MockAdapter from 'axios-mock-adapter';
import axios from 'axios';
import React from 'react';
import { render, waitFor } from '@testing-library/react';

const mock = new MockAdapter(axios);

describe('68064134', () => {
  it('should pass', async () => {
    mock.onGet('/my-url').reply(200, { data: 'hello' });

    const rendered = render(<MyComp />);

    await waitFor(() => rendered.getByTestId('data'));

    expect(rendered.getByTestId('data')).toBeTruthy();
    expect(rendered.getByTestId('data').textContent).toBe('hello');
  });
});
 

результат теста:

 PASS  examples/68064134/Component.test.tsx (12.285 s)
  68064134
    ✓ should pass (28 ms)

---------------|---------|----------|---------|---------|-------------------
File           | % Stmts | % Branch | % Funcs | % Lines | Uncovered Line #s 
---------------|---------|----------|---------|---------|-------------------
All files      |     100 |      100 |     100 |     100 |                   
 Component.tsx |     100 |      100 |     100 |     100 |                   
---------------|---------|----------|---------|---------|-------------------
Test Suites: 1 passed, 1 total
Tests:       1 passed, 1 total
Snapshots:   0 total
Time:        14.264 s