Skip to content

Commit 04ed507

Browse files
authored
Infra/useDidUpdate (#1112)
* created useDIdUpdate hook * added unittests to cover useDidUpdate hook * useDidUpdate export * typescript * remove unused * remove unused * naming * Avoid re run isEqual again by using useMemo + match dependencies type * PR Comment - logic is based on another useEffect check
1 parent 4451381 commit 04ed507

File tree

6 files changed

+99
-2
lines changed

6 files changed

+99
-2
lines changed

generatedTypes/hooks/index.d.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,2 @@
11
export { default as useToggleValue } from './useToggleValue';
2+
export { default as useDidUpdate } from './useDidUpdate';
Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,5 @@
1+
/**
2+
* This hook avoid calling useEffect on the initial value of his dependency array
3+
*/
4+
declare const useDidUpdate: (callback: () => void, dep: [any]) => void;
5+
export default useDidUpdate;

generatedTypes/index.d.ts

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -21,8 +21,7 @@ export {
2121
PaddingModifiers,
2222
TypographyModifiers,
2323
ColorsModifiers,
24-
BackgroundColorModifier,
25-
useToggleValue
24+
BackgroundColorModifier
2625
} from './commons/new';
2726
export {default as ActionBar, ActionBarProps} from './components/actionBar';
2827
export {default as Avatar, AvatarPropTypes, AvatarProps} from './components/avatar';

src/hooks/index.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1 +1,2 @@
11
export {default as useToggleValue} from './useToggleValue';
2+
export {default as useDidUpdate} from './useDidUpdate';
Lines changed: 69 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,69 @@
1+
import {renderHook} from '@testing-library/react-hooks';
2+
import useDidUpdate from '../index';
3+
4+
describe('useDidUpdate hook tests', () => {
5+
it('Expect action to not be called when the dependencies array value hasn\'t change', () => {
6+
const action = jest.fn();
7+
const dependencies = [false, 'false'];
8+
const {rerender} = renderHook(() => useDidUpdate(action, dependencies));
9+
10+
rerender();
11+
rerender();
12+
rerender();
13+
expect(action.mock.calls.length).toBe(0);
14+
});
15+
16+
it('Expect action to be called when dependencies array has change', () => {
17+
const action = jest.fn();
18+
let dependencies = [false, 'YES YES', 1];
19+
const {rerender} = renderHook(() => useDidUpdate(action, dependencies));
20+
21+
dependencies = [false, 'NO NO', 1];
22+
rerender();
23+
expect(action.mock.calls.length).toBe(1);
24+
});
25+
26+
it('Expect action to be called when dependencies array has change', () => {
27+
const action = jest.fn();
28+
let dependencies = [false, 'YES YES', 1];
29+
const {rerender} = renderHook(() => useDidUpdate(action, dependencies));
30+
31+
dependencies = [false, 'NO NO', 1];
32+
rerender();
33+
expect(action.mock.calls.length).toBe(1);
34+
});
35+
36+
it('Expect action to be called when dependencies array has change', () => {
37+
const action = jest.fn();
38+
let dependencies = [false, 'YES YES', 1];
39+
const {rerender} = renderHook(() => useDidUpdate(action, dependencies));
40+
41+
dependencies = [false, 'NO NO', 1];
42+
rerender();
43+
expect(action.mock.calls.length).toBe(1);
44+
});
45+
46+
it('Expect action to be called when object value in dependencies array has change', () => {
47+
const action = jest.fn();
48+
let dependencies = [false, [1, 2], {name: 'AAA', address: {number: 10}}];
49+
const {rerender} = renderHook(() => useDidUpdate(action, dependencies));
50+
51+
dependencies = [false, [1, 2], {name: 'BBB'}];
52+
rerender();
53+
expect(action.mock.calls.length).toBe(1);
54+
55+
dependencies = [false, [1, 2], {name: 'AAA', address: {number: 20}}];
56+
rerender();
57+
expect(action.mock.calls.length).toBe(2);
58+
});
59+
60+
it('Expect action to be called when value in array dependencies array has change', () => {
61+
const action = jest.fn();
62+
let dependencies = [false, [1, [2]], {name: 'AAA'}];
63+
const {rerender} = renderHook(() => useDidUpdate(action, dependencies));
64+
65+
dependencies = [false, [1, [3]], {name: 'AAA', address: {number: 20}}];
66+
rerender();
67+
expect(action.mock.calls.length).toBe(1);
68+
});
69+
});

src/hooks/useDidUpdate/index.ts

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
import {useEffect, useRef} from 'react';
2+
import _ from 'lodash';
3+
4+
/**
5+
* This hook avoid calling useEffect on the initial value of his dependency array
6+
*/
7+
const useDidUpdate = (callback: () => void, dep: [any]) => {
8+
const isMounted = useRef<boolean>(false);
9+
10+
useEffect(() => {
11+
if (!isMounted.current) {
12+
return;
13+
}
14+
callback();
15+
}, [dep]);
16+
17+
useEffect(() => {
18+
isMounted.current = true;
19+
}, []);
20+
};
21+
22+
export default useDidUpdate;

0 commit comments

Comments
 (0)