Skip to content

Commit 35b25b3

Browse files
authored
refactor: remove context call inside useComponents, remove getChildError (#23)
1 parent dc0485a commit 35b25b3

File tree

12 files changed

+810
-41
lines changed

12 files changed

+810
-41
lines changed
Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
import {SpecTypes} from '../constants';
2+
import {
3+
isArraySpec,
4+
isBooleanSpec,
5+
isCorrectSpec,
6+
isNumberSpec,
7+
isObjectSpec,
8+
isStringSpec,
9+
} from '../helpers';
10+
11+
describe('core/utils/common', () => {
12+
test('isCorrectSpec', () => {
13+
expect(isCorrectSpec(true)).toBe(false);
14+
expect(isCorrectSpec({})).toBe(false);
15+
expect(isCorrectSpec([])).toBe(false);
16+
expect(isCorrectSpec({type: SpecTypes.Array, viewSpec: null})).toBe(false);
17+
expect(isCorrectSpec({type: SpecTypes.Array, viewSpec: {}})).toBe(false);
18+
expect(isCorrectSpec({type: SpecTypes.Array, viewSpec: {type: null}})).toBe(false);
19+
expect(isCorrectSpec({type: SpecTypes.Array, viewSpec: {type: 'base'}})).toBe(true);
20+
});
21+
22+
test('isArraySpec', () => {
23+
expect(isArraySpec(true)).toBe(false);
24+
expect(isArraySpec({})).toBe(false);
25+
expect(isArraySpec([])).toBe(false);
26+
expect(isArraySpec({type: SpecTypes.String})).toBe(false);
27+
expect(isArraySpec({type: SpecTypes.Array})).toBe(true);
28+
});
29+
30+
test('isBooleanSpec', () => {
31+
expect(isBooleanSpec(true)).toBe(false);
32+
expect(isBooleanSpec({})).toBe(false);
33+
expect(isBooleanSpec([])).toBe(false);
34+
expect(isBooleanSpec({type: SpecTypes.String})).toBe(false);
35+
expect(isBooleanSpec({type: SpecTypes.Boolean})).toBe(true);
36+
});
37+
38+
test('isNumberSpec', () => {
39+
expect(isNumberSpec(true)).toBe(false);
40+
expect(isNumberSpec({})).toBe(false);
41+
expect(isNumberSpec([])).toBe(false);
42+
expect(isNumberSpec({type: SpecTypes.String})).toBe(false);
43+
expect(isNumberSpec({type: SpecTypes.Number})).toBe(true);
44+
});
45+
46+
test('isObjectSpec', () => {
47+
expect(isObjectSpec(true)).toBe(false);
48+
expect(isObjectSpec({})).toBe(false);
49+
expect(isObjectSpec([])).toBe(false);
50+
expect(isObjectSpec({type: SpecTypes.String})).toBe(false);
51+
expect(isObjectSpec({type: SpecTypes.Object})).toBe(true);
52+
});
53+
54+
test('isStringSpec', () => {
55+
expect(isStringSpec(true)).toBe(false);
56+
expect(isStringSpec({})).toBe(false);
57+
expect(isStringSpec([])).toBe(false);
58+
expect(isStringSpec({type: SpecTypes.Array})).toBe(false);
59+
expect(isStringSpec({type: SpecTypes.String})).toBe(true);
60+
});
61+
});

src/lib/core/components/View/ViewController.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,8 @@ export const ViewController = <SpecType extends Spec>({
1515
spec,
1616
name,
1717
}: ViewControllerProps<SpecType>) => {
18-
const {value, Link} = useDynamicFormsCtx();
19-
const {viewEntity, Layout} = useComponents(spec);
18+
const {config, value, Link} = useDynamicFormsCtx();
19+
const {viewEntity, Layout} = useComponents(spec, config);
2020
const render = useRender({name, value, spec, viewEntity, Layout, Link});
2121

2222
return <>{render}</>;
Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
import {dynamicViewConfig} from '../../../../kit';
2+
import {isCorrectViewConfig} from '../helpers';
3+
4+
describe('View/helpers', () => {
5+
test('isCorrectViewConfig', () => {
6+
expect(isCorrectViewConfig(true)).toBe(false);
7+
expect(isCorrectViewConfig({})).toBe(false);
8+
expect(isCorrectViewConfig([])).toBe(false);
9+
expect(
10+
isCorrectViewConfig({
11+
string: {
12+
view: {},
13+
layouts: {},
14+
},
15+
}),
16+
).toBe(false);
17+
expect(isCorrectViewConfig(dynamicViewConfig)).toBe(true);
18+
});
19+
});
Lines changed: 102 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,102 @@
1+
import React from 'react';
2+
3+
import {render} from '@testing-library/react';
4+
import _ from 'lodash';
5+
6+
import {Spec} from '../../../../../core';
7+
import {BaseView, ViewRow, dynamicViewConfig} from '../../../../../kit';
8+
import {SpecTypes} from '../../../../constants';
9+
import {StringSpec} from '../../../../types';
10+
import {DynamicViewConfig} from '../../types';
11+
import {useComponents} from '../useComponents';
12+
13+
const spec: StringSpec = {type: SpecTypes.String, viewSpec: {type: '', layout: ''}};
14+
15+
interface UseComponentsProps {
16+
mirror: {
17+
useComponents?: ReturnType<typeof useComponents>;
18+
};
19+
spec: Spec;
20+
config: DynamicViewConfig;
21+
}
22+
23+
const UseComponents: React.FC<UseComponentsProps> = ({mirror, spec, config}) => {
24+
mirror.useComponents = useComponents(spec, config);
25+
26+
return null;
27+
};
28+
29+
describe('View/hooks/useComponents', () => {
30+
test('incorrect config', () => {
31+
const mirror: UseComponentsProps['mirror'] = {};
32+
33+
render(<UseComponents mirror={mirror} spec={spec} config={{} as any} />);
34+
35+
expect(mirror.useComponents).toBeInstanceOf(Object);
36+
expect(mirror.useComponents?.viewEntity).toBe(undefined);
37+
expect(mirror.useComponents?.Layout).toBe(undefined);
38+
});
39+
40+
test('incorrect spec', () => {
41+
const mirror: UseComponentsProps['mirror'] = {};
42+
43+
render(<UseComponents mirror={mirror} spec={{} as any} config={dynamicViewConfig} />);
44+
45+
expect(mirror.useComponents).toBeInstanceOf(Object);
46+
expect(mirror.useComponents?.viewEntity).toBe(undefined);
47+
expect(mirror.useComponents?.Layout).toBe(undefined);
48+
});
49+
50+
test('inputEntity and Layout not found', () => {
51+
const mirror: UseComponentsProps['mirror'] = {};
52+
const _spec = _.cloneDeep(spec);
53+
54+
_spec.viewSpec.type = 'nonexistent';
55+
_spec.viewSpec.layout = 'nonexistent';
56+
57+
render(<UseComponents mirror={mirror} spec={_spec} config={dynamicViewConfig} />);
58+
59+
expect(mirror.useComponents).toBeInstanceOf(Object);
60+
expect(mirror.useComponents?.viewEntity).toBe(undefined);
61+
expect(mirror.useComponents?.Layout).toBe(undefined);
62+
});
63+
64+
test('inputEntity not found', () => {
65+
const mirror: UseComponentsProps['mirror'] = {};
66+
const _spec = _.cloneDeep(spec);
67+
68+
_spec.viewSpec.type = 'nonexistent';
69+
_spec.viewSpec.layout = 'row';
70+
71+
render(<UseComponents mirror={mirror} spec={_spec} config={dynamicViewConfig} />);
72+
73+
expect(mirror.useComponents?.viewEntity).toBe(undefined);
74+
expect(mirror.useComponents?.Layout).toBe(ViewRow);
75+
});
76+
77+
test('Layout not found', () => {
78+
const mirror: UseComponentsProps['mirror'] = {};
79+
const _spec = _.cloneDeep(spec);
80+
81+
_spec.viewSpec.type = 'base';
82+
_spec.viewSpec.layout = 'nonexistent';
83+
84+
render(<UseComponents mirror={mirror} spec={_spec} config={dynamicViewConfig} />);
85+
86+
expect(mirror.useComponents?.viewEntity?.Component).toBe(BaseView);
87+
expect(mirror.useComponents?.Layout).toBe(undefined);
88+
});
89+
90+
test('inputEntity and Layout found', () => {
91+
const mirror: UseComponentsProps['mirror'] = {};
92+
const _spec = _.cloneDeep(spec);
93+
94+
_spec.viewSpec.type = 'base';
95+
_spec.viewSpec.layout = 'row';
96+
97+
render(<UseComponents mirror={mirror} spec={_spec} config={dynamicViewConfig} />);
98+
99+
expect(mirror.useComponents?.viewEntity?.Component).toBe(BaseView);
100+
expect(mirror.useComponents?.Layout).toBe(ViewRow);
101+
});
102+
});
Lines changed: 192 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,192 @@
1+
import React from 'react';
2+
3+
import {render} from '@testing-library/react';
4+
import _ from 'lodash';
5+
6+
import {UseRenderParams, useComponents, useRender} from '../';
7+
import {FormValue, Spec} from '../../../../../core';
8+
import {BaseView, ObjectBaseView, ViewRow, dynamicViewConfig} from '../../../../../kit';
9+
import {SpecTypes} from '../../../../constants';
10+
import {AnyObject, ObjectSpec, StringSpec} from '../../../../types';
11+
import {DynamicViewConfig} from '../../types';
12+
13+
const name = 'name';
14+
const value = {name: 'value'};
15+
const spec: StringSpec = {type: SpecTypes.String, viewSpec: {type: '', layout: ''}};
16+
17+
interface UseRenderProps {
18+
mirror: {
19+
useRender?: ReturnType<typeof useRender>;
20+
};
21+
name: string;
22+
value: AnyObject;
23+
spec: Spec;
24+
config: DynamicViewConfig;
25+
Link?: React.ComponentType<{
26+
value: FormValue;
27+
link: Spec['viewSpec']['link'];
28+
}>;
29+
}
30+
31+
const UseRender: React.FC<UseRenderProps> = ({mirror, spec, config, ...rest}) => {
32+
const {viewEntity, Layout} = useComponents(spec, config);
33+
34+
mirror.useRender = useRender({spec, viewEntity, Layout, ...rest} as UseRenderParams<
35+
FormValue,
36+
Spec
37+
>);
38+
39+
return null;
40+
};
41+
42+
describe('View/hooks/useRender', () => {
43+
test('incorrect spec', () => {
44+
const mirror: UseRenderProps['mirror'] = {};
45+
46+
render(
47+
<UseRender
48+
mirror={mirror}
49+
name={name}
50+
value={value}
51+
spec={{} as any}
52+
config={dynamicViewConfig}
53+
/>,
54+
);
55+
56+
expect(mirror.useRender).toBe(null);
57+
});
58+
59+
test('incorrect name', () => {
60+
const mirror: UseRenderProps['mirror'] = {};
61+
const _spec = _.cloneDeep(spec);
62+
63+
_spec.viewSpec.type = 'base';
64+
65+
render(
66+
<UseRender
67+
mirror={mirror}
68+
name={undefined as any}
69+
value={value}
70+
spec={_spec}
71+
config={dynamicViewConfig}
72+
/>,
73+
);
74+
75+
expect(mirror.useRender).toBe(null);
76+
});
77+
78+
test('empty viewEntity', () => {
79+
const mirror: UseRenderProps['mirror'] = {};
80+
81+
render(
82+
<UseRender
83+
mirror={mirror}
84+
name={name}
85+
value={value}
86+
spec={spec}
87+
config={dynamicViewConfig}
88+
/>,
89+
);
90+
91+
expect(mirror.useRender).toBe(null);
92+
});
93+
94+
test('independent viewEntity and Layout found', () => {
95+
const mirror: UseRenderProps['mirror'] = {};
96+
const _spec: ObjectSpec = {type: SpecTypes.Object, viewSpec: {type: 'base', layout: 'row'}};
97+
98+
render(
99+
<UseRender
100+
mirror={mirror}
101+
name={name}
102+
value={value}
103+
spec={_spec}
104+
config={dynamicViewConfig}
105+
/>,
106+
);
107+
expect(mirror.useRender?.type).toBe(ObjectBaseView);
108+
expect(mirror.useRender?.props.Layout).toBe(ViewRow);
109+
});
110+
111+
test('viewEntity and Layout found', () => {
112+
const mirror: UseRenderProps['mirror'] = {};
113+
const _spec = _.cloneDeep(spec);
114+
115+
_spec.viewSpec.type = 'base';
116+
_spec.viewSpec.layout = 'row';
117+
118+
render(
119+
<UseRender
120+
mirror={mirror}
121+
name={name}
122+
value={value}
123+
spec={_spec}
124+
config={dynamicViewConfig}
125+
/>,
126+
);
127+
expect(mirror.useRender?.type).toBe(ViewRow);
128+
expect(mirror.useRender?.props.children.type).toBe(BaseView);
129+
});
130+
131+
test('viewEntity found', () => {
132+
const mirror: UseRenderProps['mirror'] = {};
133+
const _spec = _.cloneDeep(spec);
134+
135+
_spec.viewSpec.type = 'base';
136+
137+
render(
138+
<UseRender
139+
mirror={mirror}
140+
name={name}
141+
value={value}
142+
spec={_spec}
143+
config={dynamicViewConfig}
144+
/>,
145+
);
146+
expect(mirror.useRender?.type).toBe(BaseView);
147+
});
148+
149+
test('incorrect Link', () => {
150+
const mirror: UseRenderProps['mirror'] = {};
151+
const _spec = _.cloneDeep(spec);
152+
153+
_spec.viewSpec.type = 'base';
154+
_spec.viewSpec.link = 'link';
155+
156+
render(
157+
<UseRender
158+
mirror={mirror}
159+
name={name}
160+
value={value}
161+
spec={_spec}
162+
config={dynamicViewConfig}
163+
Link={null as any}
164+
/>,
165+
);
166+
expect(mirror.useRender?.props.linkValue).toBe(undefined);
167+
});
168+
169+
test('correct Link', () => {
170+
const mirror: UseRenderProps['mirror'] = {};
171+
const Link = () => null;
172+
const _spec = _.cloneDeep(spec);
173+
174+
_spec.viewSpec.type = 'base';
175+
_spec.viewSpec.link = 'link';
176+
177+
render(
178+
<UseRender
179+
mirror={mirror}
180+
name={name}
181+
value={value}
182+
spec={_spec}
183+
config={dynamicViewConfig}
184+
Link={Link}
185+
/>,
186+
);
187+
188+
expect(mirror.useRender?.props.linkValue.type).toBe(Link);
189+
expect(mirror.useRender?.props.linkValue.props.value).toBe(value[name]);
190+
expect(mirror.useRender?.props.linkValue.props.link).toBe(_spec.viewSpec.link);
191+
});
192+
});

0 commit comments

Comments
 (0)