Skip to content

Commit ae36998

Browse files
committed
Use useReducer instead of useState
1 parent af0b59c commit ae36998

File tree

4 files changed

+44
-13
lines changed

4 files changed

+44
-13
lines changed

packages/react-form-renderer/src/form-renderer/condition.js

Lines changed: 28 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import React, { useEffect } from 'react';
1+
import React, { useEffect, useReducer } from 'react';
22
import PropTypes from 'prop-types';
33
import lodashIsEmpty from 'lodash/isEmpty';
44
import get from 'lodash/get';
@@ -87,27 +87,47 @@ export const parseCondition = (condition, values) => {
8787
return negativeResult;
8888
};
8989

90+
export const reducer = (state, { type, sets }) => {
91+
switch (type) {
92+
case 'formResetted':
93+
return {
94+
...state,
95+
initial: true
96+
};
97+
case 'rememberSets':
98+
return {
99+
...state,
100+
initial: false,
101+
sets
102+
};
103+
default:
104+
return state;
105+
}
106+
};
107+
90108
const Condition = React.memo(
91109
({ condition, children, values }) => {
92110
const formOptions = useFormApi();
93111
const dirty = formOptions.getState().dirty;
94112

95-
const [lastSets, setSets] = React.useState([]);
96-
const [initial, setInitial] = React.useState(true);
113+
const [state, dispatch] = useReducer(reducer, {
114+
sets: [],
115+
initial: true
116+
});
97117

98118
const conditionResult = parseCondition(condition, values, formOptions);
99119
const setters = conditionResult.set ? [conditionResult.set] : conditionResult.sets;
100120

101121
useEffect(() => {
102122
if (!dirty) {
103-
setInitial(true);
123+
dispatch({ type: 'formResetted' });
104124
}
105125
}, [dirty]);
106126

107127
useEffect(() => {
108-
if (setters && setters.length > 0 && (initial || !isEqual(setters, lastSets))) {
128+
if (setters && setters.length > 0 && (state.initial || !isEqual(setters, state.sets))) {
109129
setters.forEach((setter, index) => {
110-
if (setter && (initial || !isEqual(setter, lastSets[index]))) {
130+
if (setter && (state.initial || !isEqual(setter, state.sets[index]))) {
111131
setTimeout(() => {
112132
formOptions.batch(() => {
113133
Object.entries(setter).forEach(([name, value]) => {
@@ -117,10 +137,9 @@ const Condition = React.memo(
117137
});
118138
}
119139
});
120-
setSets(setters);
121-
setInitial(false);
140+
dispatch({ type: 'rememberSets', sets: setters });
122141
}
123-
}, [setters, initial]);
142+
}, [setters, state.initial]);
124143

125144
return conditionResult.visible ? children : null;
126145
},

packages/react-form-renderer/src/tests/form-renderer/__snapshots__/form-renderer.test.js.snap

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -162,15 +162,15 @@ exports[`<FormRenderer /> should render form from schema 1`] = `
162162
<FormFieldHideWrapper
163163
hideField={false}
164164
>
165-
<Component
165+
<select
166166
name="secret"
167167
>
168168
<div
169169
className="nested-item"
170170
>
171171
Select field
172172
</div>
173-
</Component>
173+
</select>
174174
</FormFieldHideWrapper>
175175
</FormConditionWrapper>
176176
</SingleField>

packages/react-form-renderer/src/tests/form-renderer/__snapshots__/render-form.test.js.snap

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -451,15 +451,15 @@ exports[`renderForm function should render single field from defined componentTy
451451
<FormFieldHideWrapper
452452
hideField={false}
453453
>
454-
<Component
454+
<text-field
455455
name="foo"
456456
>
457457
<div
458458
name="foo"
459459
>
460460
TextField
461461
</div>
462-
</Component>
462+
</text-field>
463463
</FormFieldHideWrapper>
464464
</FormConditionWrapper>
465465
</SingleField>

packages/react-form-renderer/src/tests/form-renderer/condition.test.js

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@ import componentTypes from '../../../dist/cjs/component-types';
77
import useFieldApi from '../../files/use-field-api';
88
import FormRenderer from '../../files/form-renderer';
99

10+
import { reducer } from '../../form-renderer/condition';
11+
1012
const TextField = (props) => {
1113
const { input } = useFieldApi(props);
1214
return <input id={input.name} {...input} />;
@@ -306,4 +308,14 @@ describe('condition test', () => {
306308
'field-5': 'someValuu5'
307309
});
308310
});
311+
312+
describe('reducer', () => {
313+
it('returns default', () => {
314+
const initialState = {
315+
a: 'bb'
316+
};
317+
318+
expect(reducer(initialState, { type: 'nonsesne' })).toEqual(initialState);
319+
});
320+
});
309321
});

0 commit comments

Comments
 (0)