Skip to content

Commit 9432fc3

Browse files
authored
fix(jest-mock): do not restore mocks when jest.resetAllMocks() is called (#13866)
1 parent 21a9271 commit 9432fc3

File tree

3 files changed

+330
-82
lines changed

3 files changed

+330
-82
lines changed

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@
88

99
- `[jest-mock]` Clear mock state when `jest.restoreAllMocks()` is called ([#13867](https://github.com/facebook/jest/pull/13867))
1010
- `[jest-mock]` Prevent `mockImplementationOnce` and `mockReturnValueOnce` bleeding into `withImplementation` ([#13888](https://github.com/facebook/jest/pull/13888))
11+
- `[jest-mock]` Do not restore mocks when `jest.resetAllMocks()` is called ([#13866](https://github.com/facebook/jest/pull/13866))
1112

1213
### Chore & Maintenance
1314

packages/jest-mock/src/__tests__/index.test.ts

Lines changed: 236 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1247,30 +1247,6 @@ describe('moduleMocker', () => {
12471247
expect(fn.getMockName()).toBe('jest.fn()');
12481248
});
12491249

1250-
test('after mock reset, the object should return to its original value', () => {
1251-
const myObject = {bar: () => 'bar'};
1252-
1253-
const barStub = moduleMocker.spyOn(myObject, 'bar');
1254-
1255-
barStub.mockReturnValue('POTATO!');
1256-
expect(myObject.bar()).toBe('POTATO!');
1257-
barStub.mockReset();
1258-
1259-
expect(myObject.bar()).toBe('bar');
1260-
});
1261-
1262-
test('after resetAllMocks, the object should return to its original value', () => {
1263-
const myObject = {bar: () => 'bar'};
1264-
1265-
const barStub = moduleMocker.spyOn(myObject, 'bar');
1266-
1267-
barStub.mockReturnValue('POTATO!');
1268-
expect(myObject.bar()).toBe('POTATO!');
1269-
moduleMocker.resetAllMocks();
1270-
1271-
expect(myObject.bar()).toBe('bar');
1272-
});
1273-
12741250
test('mockName gets reset by mockRestore', () => {
12751251
const fn = jest.fn();
12761252
expect(fn.getMockName()).toBe('jest.fn()');
@@ -1344,6 +1320,134 @@ describe('moduleMocker', () => {
13441320
);
13451321
});
13461322

1323+
it('supports clearing a spy', () => {
1324+
let methodOneCalls = 0;
1325+
const obj = {
1326+
methodOne() {
1327+
methodOneCalls++;
1328+
},
1329+
};
1330+
1331+
const spy1 = moduleMocker.spyOn(obj, 'methodOne');
1332+
1333+
obj.methodOne();
1334+
1335+
// The spy and the original function are called.
1336+
expect(methodOneCalls).toBe(1);
1337+
expect(spy1.mock.calls).toHaveLength(1);
1338+
1339+
expect(moduleMocker.isMockFunction(obj.methodOne)).toBe(true);
1340+
1341+
spy1.mockClear();
1342+
1343+
// After clearing the spy, the method is still mock function.
1344+
expect(moduleMocker.isMockFunction(obj.methodOne)).toBe(true);
1345+
1346+
// After clearing the spy, call count is reset.
1347+
expect(spy1.mock.calls).toHaveLength(0);
1348+
});
1349+
1350+
it('supports clearing all spies', () => {
1351+
let methodOneCalls = 0;
1352+
let methodTwoCalls = 0;
1353+
const obj = {
1354+
methodOne() {
1355+
methodOneCalls++;
1356+
},
1357+
methodTwo() {
1358+
methodTwoCalls++;
1359+
},
1360+
};
1361+
1362+
const spy1 = moduleMocker.spyOn(obj, 'methodOne');
1363+
const spy2 = moduleMocker.spyOn(obj, 'methodTwo');
1364+
1365+
obj.methodOne();
1366+
obj.methodTwo();
1367+
1368+
// Both spies and both original functions are called.
1369+
expect(methodOneCalls).toBe(1);
1370+
expect(methodTwoCalls).toBe(1);
1371+
expect(spy1.mock.calls).toHaveLength(1);
1372+
expect(spy2.mock.calls).toHaveLength(1);
1373+
1374+
expect(moduleMocker.isMockFunction(obj.methodOne)).toBe(true);
1375+
expect(moduleMocker.isMockFunction(obj.methodTwo)).toBe(true);
1376+
1377+
moduleMocker.clearAllMocks();
1378+
1379+
// After clearing all mocks, the methods are still mock functions.
1380+
expect(moduleMocker.isMockFunction(obj.methodOne)).toBe(true);
1381+
expect(moduleMocker.isMockFunction(obj.methodTwo)).toBe(true);
1382+
1383+
// After clearing all mocks, call counts are reset.
1384+
expect(spy1.mock.calls).toHaveLength(0);
1385+
expect(spy2.mock.calls).toHaveLength(0);
1386+
});
1387+
1388+
it('supports resetting a spy', () => {
1389+
const methodOneReturn = 0;
1390+
const obj = {
1391+
methodOne() {
1392+
return methodOneReturn;
1393+
},
1394+
};
1395+
1396+
const spy1 = moduleMocker.spyOn(obj, 'methodOne').mockReturnValue(10);
1397+
1398+
// Return value is mocked.
1399+
expect(methodOneReturn).toBe(0);
1400+
expect(obj.methodOne()).toBe(10);
1401+
1402+
expect(moduleMocker.isMockFunction(obj.methodOne)).toBe(true);
1403+
1404+
spy1.mockReset();
1405+
1406+
// After resetting the spy, the method is still mock functions.
1407+
expect(moduleMocker.isMockFunction(obj.methodOne)).toBe(true);
1408+
1409+
// After resetting the spy, the method returns the original return value.
1410+
expect(methodOneReturn).toBe(0);
1411+
expect(obj.methodOne()).toBe(0);
1412+
});
1413+
1414+
it('supports resetting all spies', () => {
1415+
const methodOneReturn = 10;
1416+
const methodTwoReturn = 20;
1417+
const obj = {
1418+
methodOne() {
1419+
return methodOneReturn;
1420+
},
1421+
methodTwo() {
1422+
return methodTwoReturn;
1423+
},
1424+
};
1425+
1426+
moduleMocker.spyOn(obj, 'methodOne').mockReturnValue(100);
1427+
moduleMocker.spyOn(obj, 'methodTwo').mockReturnValue(200);
1428+
1429+
// Return values are mocked.
1430+
expect(methodOneReturn).toBe(10);
1431+
expect(methodTwoReturn).toBe(20);
1432+
expect(obj.methodOne()).toBe(100);
1433+
expect(obj.methodTwo()).toBe(200);
1434+
1435+
expect(moduleMocker.isMockFunction(obj.methodOne)).toBe(true);
1436+
expect(moduleMocker.isMockFunction(obj.methodTwo)).toBe(true);
1437+
1438+
moduleMocker.resetAllMocks();
1439+
1440+
// After resetting all mocks, the methods are still mock functions.
1441+
expect(moduleMocker.isMockFunction(obj.methodOne)).toBe(true);
1442+
expect(moduleMocker.isMockFunction(obj.methodTwo)).toBe(true);
1443+
1444+
// After resetting all mocks, the methods return the original return value.
1445+
expect(methodOneReturn).toBe(10);
1446+
expect(methodTwoReturn).toBe(20);
1447+
expect(obj.methodOne()).toBe(10);
1448+
expect(obj.methodTwo()).toBe(20);
1449+
});
1450+
13471451
it('supports restoring a spy', () => {
13481452
let methodOneCalls = 0;
13491453
const obj = {
@@ -1551,6 +1655,59 @@ describe('moduleMocker', () => {
15511655
);
15521656
});
15531657

1658+
it('supports resetting a spy', () => {
1659+
const methodOneReturn = 0;
1660+
const obj = {
1661+
get methodOne() {
1662+
return methodOneReturn;
1663+
},
1664+
};
1665+
1666+
const spy1 = moduleMocker
1667+
.spyOn(obj, 'methodOne', 'get')
1668+
.mockReturnValue(10);
1669+
1670+
// Return value is mocked.
1671+
expect(methodOneReturn).toBe(0);
1672+
expect(obj.methodOne).toBe(10);
1673+
1674+
spy1.mockReset();
1675+
1676+
// After resetting the spy, the method returns the original return value.
1677+
expect(methodOneReturn).toBe(0);
1678+
expect(obj.methodOne).toBe(0);
1679+
});
1680+
1681+
it('supports resetting all spies', () => {
1682+
const methodOneReturn = 10;
1683+
const methodTwoReturn = 20;
1684+
const obj = {
1685+
get methodOne() {
1686+
return methodOneReturn;
1687+
},
1688+
get methodTwo() {
1689+
return methodTwoReturn;
1690+
},
1691+
};
1692+
1693+
moduleMocker.spyOn(obj, 'methodOne', 'get').mockReturnValue(100);
1694+
moduleMocker.spyOn(obj, 'methodTwo', 'get').mockReturnValue(200);
1695+
1696+
// Return values are mocked.
1697+
expect(methodOneReturn).toBe(10);
1698+
expect(methodTwoReturn).toBe(20);
1699+
expect(obj.methodOne).toBe(100);
1700+
expect(obj.methodTwo).toBe(200);
1701+
1702+
moduleMocker.resetAllMocks();
1703+
1704+
// After resetting all mocks, the methods return the original return value.
1705+
expect(methodOneReturn).toBe(10);
1706+
expect(methodTwoReturn).toBe(20);
1707+
expect(obj.methodOne).toBe(10);
1708+
expect(obj.methodTwo).toBe(20);
1709+
});
1710+
15541711
it('supports restoring a spy', () => {
15551712
let methodOneCalls = 0;
15561713
const obj = {
@@ -1683,6 +1840,61 @@ describe('moduleMocker', () => {
16831840
expect(obj.property).toBe(true);
16841841
});
16851842

1843+
it('supports resetting a spy on the prototype chain', () => {
1844+
const methodOneReturn = 0;
1845+
const prototype = {
1846+
get methodOne() {
1847+
return methodOneReturn;
1848+
},
1849+
};
1850+
const obj = Object.create(prototype, {});
1851+
1852+
const spy1 = moduleMocker
1853+
.spyOn(obj, 'methodOne', 'get')
1854+
.mockReturnValue(10);
1855+
1856+
// Return value is mocked.
1857+
expect(methodOneReturn).toBe(0);
1858+
expect(obj.methodOne).toBe(10);
1859+
1860+
spy1.mockReset();
1861+
1862+
// After resetting the spy, the method returns the original return value.
1863+
expect(methodOneReturn).toBe(0);
1864+
expect(obj.methodOne).toBe(0);
1865+
});
1866+
1867+
it('supports resetting all spies on the prototype chain', () => {
1868+
const methodOneReturn = 10;
1869+
const methodTwoReturn = 20;
1870+
const prototype = {
1871+
get methodOne() {
1872+
return methodOneReturn;
1873+
},
1874+
get methodTwo() {
1875+
return methodTwoReturn;
1876+
},
1877+
};
1878+
const obj = Object.create(prototype, {});
1879+
1880+
moduleMocker.spyOn(obj, 'methodOne', 'get').mockReturnValue(100);
1881+
moduleMocker.spyOn(obj, 'methodTwo', 'get').mockReturnValue(200);
1882+
1883+
// Return values are mocked.
1884+
expect(methodOneReturn).toBe(10);
1885+
expect(methodTwoReturn).toBe(20);
1886+
expect(obj.methodOne).toBe(100);
1887+
expect(obj.methodTwo).toBe(200);
1888+
1889+
moduleMocker.resetAllMocks();
1890+
1891+
// After resetting all mocks, the methods return the original return value.
1892+
expect(methodOneReturn).toBe(10);
1893+
expect(methodTwoReturn).toBe(20);
1894+
expect(obj.methodOne).toBe(10);
1895+
expect(obj.methodTwo).toBe(20);
1896+
});
1897+
16861898
it('supports restoring a spy on the prototype chain', () => {
16871899
let methodOneCalls = 0;
16881900
const prototype = {

0 commit comments

Comments
 (0)