首页 > 解决方案 > React、Enzyme 异步生命周期函数

问题描述

我的组件上有一个异步componentDidMount函数,它进行 API 调用并更新mobx商店。组件有@observer注释。

我已经模拟了 API,但我遇到了麻烦 - 我无法弄清楚如何在我的测试中等待该生命周期方法:

 it("Magick", async () => {
    const comp = await mount(<Comp/>); // -- no point of await here

    // await comp.instance().componentDidMount(); -- should work, even if function is called wtice
    // await new Promise((resolve) => setTimeout(resolve, 100)); // -- smelly and prone to crashing

    expect(Axios.post).toBeCalledTimes(1);
    expect(MobX.value).toBe(-1);

    comp.unmount();
});

组件片段:

 componentDidMount = async () => {
    try {
        const result = await AxiosWrapper.GetValue();

        if (result) {
            const errors = Parser.getErrors(result);
            if (errors) {
                console.log(errors);
            } else {
                MobX.value = Parser.getValue(result)
            }
        }
    } catch (e) {
        console.log(e);
    }
};

axios 封装方法:

static async GetValue() {
    return await Axios.post(...);
}

我发现的唯一解决方案是添加超时,但这是不可接受的。我发现的任何其他解决方案都不起作用 - 有什么想法吗?

标签: reactjsjestjsenzymemobx

解决方案


为了使组件可测试,应该有一个承诺链。这个组件的问题在于它componentDidMount是实例方法,在组件实例化之前它不能被窥探或模拟。相反,它应该是:

async componentDidMount() {
  ...
}

然后可以在类原型上监视它:

const cdmSpy = jest.spyOn(Comp.prototype, 'componentDidMount');
const comp = mount(<Comp/>);
await cdmSpy.mock.results[0].value;
...

或者,componentDidMount可以手动调用并与 EnzymedisableLifecycleMethods选项一起测试。


推荐阅读