【问题标题】:Update store with Apollo mutation when testing with MockedProvider使用 MockedProvider 进行测试时使用 Apollo 突变更新存储
【发布时间】:2019-03-23 03:48:18
【问题描述】:

我正在尝试测试在运行突变后应该使用新数据更新的组件。我在下面发布了示例代码。你可以找到它on GitHub as runnable repository as well

不幸的是,我没有找到一种方法在突变后实际更新MockedProvider 的存储数据。当您运行测试时,您可以看到正在执行突变并且组件在此之后被渲染。但是由于突变没有做任何事情,所以没有添加新的待办事项。

谁能告诉我在使用MockedProvider 时如何通过突变更改数据?

测试查询和变异:

const TODOS_QUERY = gql`
  query todos {
    todos {
      title
    }
  }
`

const ADD_TODO_MUTATION = gql`
  mutation addTodo($title: String!) {
    addTodo(title: $title)
  }
`;

测试组件:

const Component = () => (
  <Query query={TODOS_QUERY}>
    {
      ({ data }) => {
        console.log('render'); return (
        <Mutation mutation={ADD_TODO_MUTATION}>
          {
            addTodo => (
              <div>
                <button onClick={() => { console.log('addTodo'); addTodo({ variables: { title: 'My new todo' } }) }}>
                  Click me to add a todo!
                </button>

                {
                  (data.todos || []).map(({ title }, index) => (
                    <div key={index} className="todo-item">
                      {title}
                    </div>
                  ))
                }
              </div>
            )
          }
        </Mutation>
      )}
    }
  </Query>
);

测试实现。这会使用 Enzyme 挂载组件,模拟单击按钮执行突变并等待组件再次渲染。

it('renders without crashing', async () => {
  const mocks = [
    {
      request: {
        query: TODOS_QUERY,
      },
      result: {
        data: {
          todos: [
            {
              title: 'An old todo',
            },
          ],
        },
      },
    },
    {
      request: {
        query: ADD_TODO_MUTATION,
        variables: {
          title: 'My new todo',
        },
      },
      result: {
        data: {
          addTodo: null,
        },
      },
    },
  ];

  const wrapper = mount(
    <MockedProvider mocks={mocks} addTypename={false}>
      <Component />
    </MockedProvider>
  );

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

  console.log(wrapper.debug())

  expect(wrapper.contains('An old todo')).toBe(true);
  expect(wrapper.contains('My new todo')).toBe(false);
  wrapper.find('button').simulate('click');

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

  console.log(wrapper.debug())

  expect(wrapper.contains('An old todo')).toBe(true);
  expect(wrapper.contains('My new todo')).toBe(true);
});

非常感谢您的帮助!

【问题讨论】:

    标签: reactjs jestjs enzyme apollo react-apollo


    【解决方案1】:

    MockedProvider 接受一个 cache 属性,您可以将自己的缓存传递给它(与您在初始化 ApolloClient 时使用的相同)。这应该会在测试中为您提供自动缓存更新。

    您可能需要删除addTypeName=false 才能使其工作,并提供包括__typenames 在内的模拟。

    https://www.apollographql.com/docs/react/api/react-testing/

    【讨论】:

      猜你喜欢
      • 2019-03-08
      • 2018-11-02
      • 2019-10-24
      • 2018-12-19
      • 2013-01-11
      • 2020-05-09
      • 2018-12-20
      • 1970-01-01
      • 2018-08-02
      相关资源
      最近更新 更多