使用act函数jest js创建多个异步测试时出错

时间:2020-10-05 23:01:39

标签: reactjs async-await jestjs integration-testing enzyme

在这种情况下,我正在做一个示例项目,该项目试图在第一次加载组件时以及单击按钮以获取新短语时显示短语和短语的作者。测试的问题是我试图模拟用户与应用程序交互的方式,并且异步进行两个测试,每个测试都有act()函数,我得到以下错误:

console.error node_modules/react-dom/cjs/react-dom-test-utils.development.js:87      
  Warning: You seem to have overlapping act() calls, this is not supported. Be sure to await previous act() calls before making a new one. 
console.error node_modules/react-dom/cjs/react-dom.development.js:88
  Warning: An update to QuoteContainer inside a test was not wrapped in act(...).    
  
  When testing, code that causes React state updates should be wrapped into act(...):      
  act(() => {
    /* fire events that update state */
  });
  /* assert on the output */
  
  This ensures that you're testing the behavior the user would see in the browser.
      in QuoteContainer (created by WrapperComponent)
      in WrapperComponent
console.error node_modules/react-dom/cjs/react-dom.development.js:88
  Warning: An update to QuoteContainer inside a test was not wrapped in act(...).    
  
  When testing, code that causes React state updates should be wrapped into act(...):      
  act(() => {
    /* fire events that update state */
  });
  /* assert on the output */
  
  This ensures that you're testing the behavior the user would see in the browser.
      in QuoteContainer (created by WrapperComponent)
      in WrapperComponent
console.error node_modules/react-dom/cjs/react-dom.development.js:88
  Warning: An update to QuoteContainer inside a test was not wrapped in act(...).    
  
  When testing, code that causes React state updates should be wrapped into act(...):      
  act(() => {
    /* fire events that update state */
  });
  /* assert on the output */
  
  This ensures that you're testing the behavior the user would see in the browser.
      in QuoteContainer (created by WrapperComponent)
      in WrapperComponent

测试通过,但是会生成此警报。我已经在寻找替代方法,例如避免异步测试,但是当测试未通过时,这迫使我将等待状态付诸实践。

这个例子很简单,但是我想在更复杂的应用程序中应用同样的测试,以验证它的正确操作。因此,可能有必要进行更多的异步测试。

这是容器组件:

import React, {
  useEffect,
  useState,
} from "react";

import Quote from "./quote.component";

import { getQuote } from "../../repository/quote.repository";

const QuoteContainer = () => {
  const [quote, setQuote] = useState("");
  const [author, setAuthor] = useState("");
  const [isLoading, setLoading] = useState(true);

  useEffect(() => {
    getQuoteData();
  }, []);

  const newQuoteHandler = () => {
    getQuoteData();
  };

  const getQuoteData = async () => {
    const {
      quoteText,
      quoteAuthor,
    } = await getQuote();
    setAuthor(quoteAuthor);
    setQuote(quoteText);
    setLoading(false);
  };

  return (
    <Quote
      isLoading={isLoading}
      quote={quote}
      author={author}
      newQuoteHandler={newQuoteHandler}
    />
  );
};

export default QuoteContainer;

与容器相关的测试:

import React from "react";
import { server, rest } from "../../mocks/server";
import waitForExpect from "wait-for-expect";

import { mount } from "../../enzymeConfig";

import QuoteContainer from "./quote.container";

import { act } from "react-dom/test-utils";

import { QuoteText } from "../quote/quote.style";
import { SpinnerContainer } from "../withSpinner/withSpinner.style";

describe("testing quote api", () => {

  it("should render spinner on start", () => {
    const wrapper = mount(<QuoteContainer />);
    expect(
      wrapper.find(SpinnerContainer)
    ).toHaveLength(1);
  });

  it("should render actual component on load information", async (done) => {
    expect.assertions(1);

    const wrapper = mount(<QuoteContainer />);

    await act(async () => {
      await waitForExpect(() => {
        wrapper.update();
        expect(
          wrapper.find(QuoteText).text()
        ).toEqual(
          "Know how to listen, and you will profit even from those who talk badly."
        );
        done();
      });
    });
  });

  it("should change quote and author when Quote Button click", async (done) => {
    const wrapper = mount(<QuoteContainer />);

    await act(async () => {
      await waitForExpect(() => {
        wrapper.update();
        expect(
          wrapper.find(QuoteText).text()
        ).toEqual(
          "Know how to listen, and you will profit even from those who talk badly."
        );
        done();
      });
    });

    rest.get(
      "apiURL",
      (req, res, ctx) =>
        res(
          ctx.status(200),
          ctx.json({
            quoteText: "this is an other frase",
            quoteAuthor: "Plutarch ",
            senderName: "",
            senderLink: "",
          })
        )
    );

    wrapper
      .find(CustomButton)
      .at(0)
      .simulate("click");

    await act(async () => {
      await waitForExpect(() => {
        wrapper.update();
        expect(
          wrapper.find(QuoteText).text()
        ).toEqual("this is an other frase");
        done();
      });
    });
  });
});

从现在开始谢谢

0 个答案:

没有答案