React Apollo MockProvider总是加载,从不提供数据

时间:2017-09-06 16:40:13

标签: reactjs mocking graphql enzyme react-apollo

我试图测试使用graphql的组件,但是当使用Apollo的MockProvider时,我从来没有得到数据,只是每次都说loading = true。

一个完整的极简主义示例是here

我尝试的事情:

      
  1. 在线查找(找到this similar question,但由于没有回答,我想我会更新一个有更多信息)
  2. 在测试(export function Component)时尝试不使用graphql导出组件,但在测试嵌套组件时不起作用
  3. 尝试尽可能简化(结果在示例中)

3 个答案:

答案 0 :(得分:2)

是的,我也遇到了这个问题。有趣的是,如果我将控制台日志添加到组件本身,则可以看到数据最终到达那里。但是出于某种原因,wrapper仍只包含我们的“正在加载...”用户界面。

原来,您需要调用wrapper.update()来使包装器重新呈现其内容。

这是对我有用的方法,但似乎不理想,因此,如果有其他解决方法,请告诉我!现在,我们的测试如下所示:

it('should render the HeroDiv if there is guide data', async () => {
  const wrapper = mount(
    <MockedProvider mocks={mocksWithGuideData} addTypename={false}>
      <Hero {...props} />
    </MockedProvider>
  );

  await wait(0);
  wrapper.update();

  expect(wrapper.find('HeroDiv').exists()).toBeTruthy();
})

答案 1 :(得分:2)

我不喜欢await wait(0)方法。查看阿波罗文档:

For more complex UI with heavy calculations, or delays added into its render logic, the wait(0) will not be long enough.

这意味着您的测试可能会不稳定。为了解决此问题,我使用了wait-for-expect包(文档中也介绍了https://www.apollographql.com/docs/guides/testing-react-components.html#Testing-mutation-components):

it('should render the HeroDiv if there is guide data', async () => {
  const wrapper = mount(
    <MockedProvider mocks={mocksWithGuideData} addTypename={false}>
      <Hero {...props} />
    </MockedProvider>
  );

  await waitForExpect(() => {
    wrapper.update();
    expect(wrapper.find('HeroDiv').exists()).toBeTruthy();
  });
})

waitForExpect实际上将轮询直到条件完成,并且在5秒钟后超时。只要您的查询在5秒之前完成,这就能保证您的测试能够完成,如果您使用的是MockedProvider,则绝对可以。

文档指出了一个警告:The risk of using a package like this everywhere by default is that every test could take up to five seconds to execute (or longer if the default timeout has been increased).但根据我的经验,使用MockedProvider绝不会发生这种情况。另外,await wait(0)始终无法始终如一地处理这种情况。

答案 2 :(得分:0)

此外,请确保要在组件文件中导入的查询与在测试文件中使用的查询完全相同。例如,我遇到了一个问题,即我的模拟道具无法将任何数据传递给MockedProvider,因为我正在导入:

import { CURRENT_USER_QUERY } from '../lib/queries';

在PleaseSigin.js中,我正在导入:

import { CURRENT_USER_QUERY } from './User';

在PleaseSignin.test.js中。显然,即使两个查询都相同,但就Jest而言,它们并不相同。