Как правильно протестировать отклоненную функцию в асинхронном компоненте React? - PullRequest
0 голосов
/ 26 июня 2018

Мой компонент реагирования выполняет асинхронный запрос для получения некоторых данных, используя lodash debounce - поскольку пользовательский ввод может вызвать повторные запросы, и я хочу ограничить скорость запросов - и затем установить состояние компонентас результатами, которые возвращаются.

MyComponent (React Component)

componentWillMount() {
  this.runQuery();
}

handler = (response) => {
   this.setState({ results: response.results });
}

runQuery = _.debounce((props = this.props) => {
  // run the query
  doStuff(mainParams)
    .withSomeOtherStuff(moreParams)
    .query()
    .then(this.handler)
    .catch((error) => {
      this.props.catchError(error);
    });
}, 200);

В настоящее время я отключаю свою основную точку выхода API, которая выходит и выбирает данныекоторый возвращает обещание благодаря пакету sinon-stub-promise

before((done) => {
  stub = stubGlobalFn('evaluate'); // returns stubbed promise, uses npm:sinon-stub-promise
});

Это позволяет мне использовать мой пользовательский Reader (проверенный в другом месте) для чтения ложного ответа, а затем разрешать его синхронно для целей тестирования.

mytest.spec.jsx

  let stub;
  const testWithProps = props => (
    new Promise((resolve, reject) => {
      new Reader(histories).readGrid((err, grid) => {
        try {
          expect(err).to.be.a('null');
          stub.resolves(grid);
          // ....

Затем в той же функции testWithProps я могу смонтировать компонент Table с помощью опор, указанных вмой тест как своего рода фабрика тестов.

const wrapper = mount(<Table {...props} />);

И вот тут я натолкнулся на замешательство. Я затушевал обещание, которое разрешается, когда вызывается основная асинхронная функция evaluate.t не обработчик состояния.

stub.thenable.then(() => {
  // --------------------------
  // PROBLEM: how to test without setting a timeout?
  // --------------------------
  setTimeout(() => {
    resolve(wrapper.update());
  }, 200);
  // --------------------------
  // --------------------------
});

Должен ли я вместо этого заглушить свою функцию handler внутри моего компонента реагирования, если я хочу проверить состояние компонента после асинхронное поведение?Я не уверен, как даже заглушить эту часть, если это даже то, что нужно.

В конце концов мой тест будет выглядеть примерно так:

it('toggles the row for the value when clicked', () => {
  const props = {
    // some props that I use
  };

  return testWithProps(props).then((wrapper) => {
    // simply testing that my mocked response made it in successfully to the rendered component
    expect(wrapper.state().results.length).to.equal(4);
  });
});
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...