Я не думаю, что это возможно, чтобы увеличить существующий интерфейс для добавления некоторых свойств к способам, объявленным в этом интерфейсе.
Но вы можете переопределить эти методы. Существует способ избежать написания типов бросков все время: вы можете определить свой собственный интерфейс MockWindow
, имеющий addEventListener
и removeEventListener
, набранный по мере необходимости. Тогда вы можете бросить реальный window
объект MockWindow
один раз и использовать его впоследствии:
interface MockWindow extends Window {
addEventListener: jest.Mock<{}> & typeof window.addEventListener;
removeEventListener: jest.Mock<{}> & typeof window.removeEventListener;
}
function mockWindow() {
window.addEventListener = jest.fn();
window.removeEventListener = jest.fn();
return window as MockWindow;
}
let w = mockWindow();
w.addEventListener('load',function() {});
w.addEventListener.mockClear();
На самом деле, потому что в текущей версии шутя типизации, jest.Mock
интерфейс уже имеет очень рыхлую вызов подписи
interface Mock<T> extends Function {
...
(...args: any[]): any;
ничего объявленную поскольку jest.Mock
можно вызывать с любым количеством любых параметров, и это делает ненужным добавление & typeof window.addEventListener
к типу addEventListener
.
UPDATE: оказывается машинопись достаточно выразительным, так что вы можете написать универсальный, тип проверил функцию:
function mockMethods<T, MethodName extends keyof T>(o: T, methodNames:MethodName[])
: T & {[K in MethodName]: T[K] & jest.Mock<{}>} {
methodNames.forEach(k => {
o[k] = jest.fn() as any;
});
return o as any; // typescript doesn't allow this cast:
// as (T & {[K in MethodKeys]: T[K] & jest.Mock<{}>});
}
let w = mockMethods(window, ['addEventListener', 'removeEventListener']);
w.addEventListener('load', function() {});
w.addEventListener.mockClear();
// you can still call other window methods
w.alert('x');
// and their types are unaffected
w.alert.mockClear(); // error: Property 'mockClear' does not exist
// on type '(message?: any) => void'.
// and you can't mock non-existent methods
let u = mockMethods(window, ['z']); // error: Argument of type '"z"[]'
// is not assignable to parameter of type '("blur" | ...
Спасибо большое, очень чистый, лаконичный и ясный ответ. Работает как шарм :) –