Как проверить переполнение div и показать больше / показать меньше функциональности с помощью библиотеки реагирующего тестирования - PullRequest
0 голосов
/ 19 марта 2020

У меня есть компонент, который отображает текст и показывает show more ссылку с многоточием ..., если текст переполняется. Когда пользователь нажимает show more, ссылка изменяется на show less, и весь текст отображается без многоточия ....

TestApp.tsx

import React from 'react';
import './styles.css';

export default function App(props: any) {
  const ref: any = React.createRef();
  const [showMore, setShowMore] = React.useState(false);
  const [showLink, setShowLink] = React.useState(false);

  React.useLayoutEffect(() => {
    if (ref.current.clientWidth < ref.current.scrollWidth) {
      setShowLink(true);
    }
  }, [ref]);

  const onClickMore = () => {
    setShowMore(!showMore);
  };

  const renderMore = () => {
    return (
      <span className='link' onClick={onClickMore}>
        {showMore ? 'show less' : 'show more'}
      </span>
    );
  };

  return (
    <div>
      <div ref={ref} className={showMore ? '' : 'container'}>
        {props.list.join(', ')}
      </div>
      {showLink && renderMore()}
    </div>
  );
}

стили. css

.container {
  overflow-x: hidden;
  text-overflow: ellipsis;
  white-space: nowrap;
  width: 200px;
}

.link {
  text-decoration: underline;
  cursor: pointer;
  color: #0d6aa8;
}

Я хочу протестировать этот компонент. Ниже приведены утверждения, которые я хочу сделать

Given that text is not overflowing
1. Show more link should not be displayed
2. Entire text should be displayed

Given that text is overflowing
1. Show more link should be displayed 
2. Entire text should not be displayed

 When show more link is clicked
  1. Show less link should be displayed
  2. Show more link should not be displayed
  3. Entire text should be displayed

  When show less link is clicked
   1. Show more link should be displayed
   2. Show less link should not be displayed
   3. Entire text should not be displayed

Теперь тестирование сценария, в котором текст не переполняется, достаточно просто. Но тестирование сценария, в котором текст переполняется, оказывается трудным. Поскольку я показываю show more ссылку, когда clientWidth < scrollWidth компонента и во время тестирования, оба эти значения кажутся равными 0. Я обнаружил проблему github в repo реагирующей-библиотеки-репозитории , и я попытался проверить это следующими способами

TestApp.test.tsx

import { fireEvent, render } from '@testing-library/react';
import React from 'react';
import App from './TestApp';

describe('When user views list', () => {
    describe('When text does not overflow', () => {
      test('that show more text is not displayed', async () => {
        const props = { list: ['value1', 'value2', 'value3'] };
        const { queryByText } = render(<App {...props} />);
        expect(queryByText('show more')).toBeNull();
      });

      test('that entire violation text is shown', async () => {
        const props = { list: ['value1', 'value2', 'value3'] };
        const { getByText } = render(<App {...props} />);
        expect(getByText(props.list.join(', '))).toBeDefined();
      });
    });

    describe('When text overflows', () => {
      let props: any;
      let list: string[];
      let text: string;
      let getByText: any;
      let queryByText: any;
      const showMoreText = 'show more';
      const showLessText = 'show less';
      beforeEach(() => {
        list =  Array.from({ length: 20 }, (_, index) => `value${index}`);
        props = { list };
        text = list.join(', ');
      });

      beforeAll(() => {
        Object.defineProperty(window.HTMLHtmlElement.prototype, 'clientWidth', { configurable: true, value: 100 });
        Object.defineProperty(window.HTMLHtmlElement.prototype, 'scrollWidth', { configurable: true, value: 200 });
        const component = render(<App {...props} />);
        getByText = component.getByText;
        queryByText = component.queryByText;
      });

      afterAll(() => {
        Object.defineProperty(window.HTMLHtmlElement.prototype, 'clientWidth', { configurable: true, value: 0 });
        Object.defineProperty(window.HTMLHtmlElement.prototype, 'scrollWidth', { configurable: true, value: 0 });
      });

      test('that show more link is displayed', async () => {
        expect(getByText(showMoreText)).toBeDefined();
      });

      test('that entire text is not displayed', async () => {
        expect(queryByText(list)).toBeNull();
      });

      describe('When user clicks on show more link', () => {
        beforeAll(() => {
          fireEvent.click(getByText(showMoreText));
        });

        test('that show more link is not displayed anymore', async () => {
          expect(queryByText(showMoreText)).toBeNull();
        });

        test('that show less link is displayed', async () => {
          expect(getByText(showLessText)).toBeDefined();
        });

        test('that entire text is displayed', async () => {
          expect(getByText(text)).toBeDefined();
        });

        describe('When user clicks on show less link', () => {
          beforeAll(() => {
            fireEvent.click(getByText(showLessText));
          });

          test('that show less link is not displayed anymore', async () => {
            expect(queryByText(showLessText)).toBeNull();
          });

          test('that show more link is displayed again', async () => {
            expect(getByText(showMoreText)).toBeDefined();
          });

          test('that entire text is not displayed', async () => {
            expect(queryByText(text)).toBeNull();
          });
        });
      });
    });
  });

Но это не работает. Как правильно проверить этот компонент?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...