更新答案(2021 年 5 月)
我在线程中的很多答案中遇到了一些问题。我认为随着时间的推移对底层库的版本更改导致了损坏。
我的配置:
"typescript": "~4.1.5"
"jest": "^26.6.3"
"jest-environment-jsdom": "^26.6.2"
另外,我应该注意,我的解决方案非常冗长。但是我的用例需要测试window.location.replace() 和结果。所以我不能
简单地模拟window.location.replace。如果您只需要模拟其中一个函数而不关心实际的href 的变化,那么线程中的一些解决方案将使用更少的代码工作得很好。
工作版本
我发现完全填充 window.location 对象解决了我所有的问题。
window.locationpolyfill
使用此代码并将其放在测试文件或设置文件中的任何位置:
export class MockWindowLocation {
private _url: URL = new URL();
get href (): string {
return this._url.toString();
}
set href (url: string) {
this._url = new URL(url);
}
get protocol (): string {
return this._url.protocol;
}
get host (): string {
return this._url.host;
}
get hostname (): string {
return this._url.hostname;
}
get origin (): string {
return this._url.origin;
}
get port (): string {
return this._url.port;
}
get pathname (): string {
return this._url.pathname;
}
get hash (): string {
return this._url.hash;
}
get search (): string {
return this._url.search;
}
replace = jest.fn().mockImplementation((url: string) => {
this.href = url;
});
assign = jest.fn().mockImplementation((url: string) => {
this.href = url;
});
reload = jest.fn();
toString(): string {
return this._url.toString();
}
}
测试一下
然后你必须删除window.location并将其设置为新的polyfill:
it('should be able to test window.location', () => {
delete window.location;
Object.defineProperty(window, 'location', {
value: new MockWindowLocation()
});
window.location.href = 'https://example.com/app/#/route/1';
window.location.reload();
expect(window.location.reload).toHaveBeenCalled();
expect(window.location.href).toBe('https://example.com/app/#/route/1');
expect(window.location.pathname).toBe('/app/');
expect(window.location.hash).toBe('#/route/1');
});
这对我来说很神奇。希望它可以帮助其他人。
其他答案更简单
再次重申,此线程中还有其他可以正常工作的答案。我发现:
Object.defineProperty(window, 'location', {
writable: true,
value: { reload: jest.fn() },
});
还有:
const location: Location = window.location;
delete window.location;
window.location = {
...location,
reload: jest.fn()
};
两者都有帮助。但就像我说的,我需要监视 replace() 并且仍然拥有 window.location 的标准功能。
希望这对某人有所帮助。干杯!