toHaveBeenCalledWith() error: Expected 2 arguments, but got 1

toHaveBeenCalledWith() error: Expected 2 arguments, but got 1

在组件 .ts 文件中

onScrollToProductSelector(){
   let offset = document.getElementById("selector").offsetTop;
   window.scrollBy({
      top: offset,
      behavior: "smooth"
   });
}

.spec.ts文件中

it("should call window.scrollby", () => {
        spyOn<any>(window, "scrollBy");
        let topOffset = fixture.debugElement.nativeElement.querySelector("#selector").offsetTop;
        const mockObj = {
            top: topOffset,
            behavior: "smooth"
        }
        component.onScrollToProductSelector();
        expect(window.scrollBy).toHaveBeenCalledWith(mockObj);
});

但是当我 运行 这个测试用例时,出现以下错误:

error TS2554: Expected 2 arguments, but got 1.

此问题是由于 DefinitelyTyped 问题 #42455

Window.scrollBy() 是重载方法。

window.scrollBy(x-coord, y-coord);
window.scrollBy(options) 

您在代码中使用的是 window.scrollBy(options) 版本,但 toHaveBeenCalledWith 试图找到 window.scrollBy(x-coord, y-coord) 的匹配项。

显然有办法解决这个问题。仔细阅读 DefinitelyTyped#42455 中的评论,然后选择最适合您的评论。

正如@uminder 建议的那样#42455,

window.scrollBy 是一个重载方法,默认情况下它正在考虑 2 参数重载方法。 window.scrollBy(x, y);

解决方案是:不检查是否使用 ... 参数调用方法,检查第一个参数是否为 ... 参数对象。

it("should call window.scrollby", () => {
        let spyCall = spyOn<any>(window, "scrollBy");
        let topOffset = fixture.debugElement.nativeElement.querySelector("#selector").offsetTop;
        const mockObj = {
            top: topOffset,
            behavior: "smooth"
        }
        component.onScrollToProductSelector();
        expect(spyCall.calls.argsFor(0)).toEqual([mockObj]);
});