Jest将对象传递给expect().toBeCalledWith()

cetgtptt  于 2023-04-27  发布在  Jest
关注(0)|答案(3)|浏览(234)

我用jest测试react组件,用expect(...).toBeCalledWith(...);测试一个函数是否被特定参数调用,并且它在值类型上工作得很好。
问题是我想测试一个以object为参数的函数,所以当你调用expect(myFunc).toBeCalledWith(object);时,测试总是失败,因为两个对象之间的引用当然不一样。
那么我该如何解决这个问题呢?
我想测试的一个示例代码是

it('the function should be called with the correct object', () => {
    api.submitForm = jest.fn().mockReturnValue(Promise.resolve());
    const wrapper = shallow(<component />);
    const instance = wrapper.instance();
    instance.submitForm();
    const object = {
      foo : 'foo',
      bar: 'bar'
    };
    // this always fails even the function is called with the same object values
    expect(api.submitForm).toBeCalledWith(object);
  });

错误消息类似于以下内容

Expected mock function to have been called with:
      [{"bar": "bar", "foo": "foo"}]
    But it was called with:
      [{"bar": "bar", "foo": "foo"}]

更新

看起来下面的代码工作正常

expect(api.submitForm).toBeCalledWith(
    expect.objectContaining({
     foo : 'foo',
      bar: 'bar'
    }),
  );

但是,如果对象包含具有数组值的属性,则上述解决方案不起作用

const obj = {
  foo : ['foo1', 'foo2'],
  bar: 'bar'
}
qnakjoqk

qnakjoqk1#

查看jest文档(https://jestjs.io/docs/expect#expectobjectcontainingobject)。看起来你可以这样做:

expect(api.submitForm).toBeCalledWith(
    expect.objectContaining({
     foo : 'foo',
      bar: 'bar'
    }),
  );
6l7fqoea

6l7fqoea2#

可以使用.mock.calls[callIdx][paramIdx]
描述+示例:https://stackoverflow.com/a/41939921/2519073
在你的情况下

expect(api.submitForm.mock.calls[0][0]).toMatchObject( // use whatever matcher you want
    {
      foo : ['foo1', 'foo2'],
      bar: 'bar'
    },
  );
y3bcpkx1

y3bcpkx13#

如果你的函数是带参数调用的

function update( userId, partialUserObject ){
   // update logic
}

你可以用

expect(update).toBeCalledWith('mockUserId',
   expect.objectContaining({
     username:'hello-world',
     displayName: 'Hello World'
   })
);
  • 数组:https://jestjs.io/docs/expect#expectarraycontainingarray
  • 对象:https://jestjs.io/docs/expect#expectobjectcontainingobject

相关问题