@samitouri / QOS-React / commits / a22880e5e5

Add support for Suspense & lazy() to the react-is package (#14423)

* Add support for lazy & Suspense to react-is

Pleun Vanderbauwhede committed Dec 12, 2018 at 19:56 UTC a22880e5e59d5cb17fffe04af093ea54e356538d
2 files changed +38 -6
packages/react-is/src/ReactIs.js
+16 -4
@@ -16,11 +16,13 @@ import {
16 REACT_ELEMENT_TYPE,
17 REACT_FORWARD_REF_TYPE,
18 REACT_FRAGMENT_TYPE,
19 + REACT_LAZY_TYPE,
20 REACT_MEMO_TYPE,
21 REACT_PORTAL_TYPE,
22 REACT_PROFILER_TYPE,
23 REACT_PROVIDER_TYPE,
24 REACT_STRICT_MODE_TYPE,
25 + REACT_SUSPENSE_TYPE,
26 } from 'shared/ReactSymbols';
27 import isValidElementType from 'shared/isValidElementType';
28 import lowPriorityWarning from 'shared/lowPriorityWarning';
@@ -38,6 +40,7 @@ export function typeOf(object: any) {
40 case REACT_FRAGMENT_TYPE:
41 case REACT_PROFILER_TYPE:
42 case REACT_STRICT_MODE_TYPE:
43 + case REACT_SUSPENSE_TYPE:
44 return type;
45 default:
46 const $$typeofType = type && type.$$typeof;
@@ -51,6 +54,7 @@ export function typeOf(object: any) {
54 return $$typeof;
55 }
56 }
57 + case REACT_LAZY_TYPE:
58 case REACT_MEMO_TYPE:
59 case REACT_PORTAL_TYPE:
60 return $$typeof;
@@ -68,10 +72,12 @@ export const ContextProvider = REACT_PROVIDER_TYPE;
72 export const Element = REACT_ELEMENT_TYPE;
73 export const ForwardRef = REACT_FORWARD_REF_TYPE;
74 export const Fragment = REACT_FRAGMENT_TYPE;
71 -export const Profiler = REACT_PROFILER_TYPE;
72 -export const Portal = REACT_PORTAL_TYPE;
75 +export const Lazy = REACT_LAZY_TYPE;
76 export const Memo = REACT_MEMO_TYPE;
77 +export const Portal = REACT_PORTAL_TYPE;
78 +export const Profiler = REACT_PROFILER_TYPE;
79 export const StrictMode = REACT_STRICT_MODE_TYPE;
80 +export const Suspense = REACT_SUSPENSE_TYPE;
81
82 export {isValidElementType};
83
@@ -114,8 +120,8 @@ export function isForwardRef(object: any) {
120 export function isFragment(object: any) {
121 return typeOf(object) === REACT_FRAGMENT_TYPE;
122 }
117 -export function isProfiler(object: any) {
118 - return typeOf(object) === REACT_PROFILER_TYPE;
123 +export function isLazy(object: any) {
124 + return typeOf(object) === REACT_LAZY_TYPE;
125 }
126 export function isMemo(object: any) {
127 return typeOf(object) === REACT_MEMO_TYPE;
@@ -123,6 +129,12 @@ export function isMemo(object: any) {
129 export function isPortal(object: any) {
130 return typeOf(object) === REACT_PORTAL_TYPE;
131 }
132 +export function isProfiler(object: any) {
133 + return typeOf(object) === REACT_PROFILER_TYPE;
134 +}
135 export function isStrictMode(object: any) {
136 return typeOf(object) === REACT_STRICT_MODE_TYPE;
137 }
138 +export function isSuspense(object: any) {
139 + return typeOf(object) === REACT_SUSPENSE_TYPE;
140 +}
packages/react-is/src/__tests__/ReactIs-test.js
+22 -2
@@ -39,17 +39,19 @@ describe('ReactIs', () => {
39 }
40
41 const FunctionComponent = () => React.createElement('div');
42 -
42 const ForwardRefComponent = React.forwardRef((props, ref) =>
43 React.createElement(Component, {forwardedRef: ref, ...props}),
44 );
46 -
45 + const LazyComponent = React.lazy(() => Component);
46 + const MemoComponent = React.memo(Component);
47 const Context = React.createContext(false);
48
49 expect(ReactIs.isValidElementType('div')).toEqual(true);
50 expect(ReactIs.isValidElementType(Component)).toEqual(true);
51 expect(ReactIs.isValidElementType(FunctionComponent)).toEqual(true);
52 expect(ReactIs.isValidElementType(ForwardRefComponent)).toEqual(true);
53 + expect(ReactIs.isValidElementType(LazyComponent)).toEqual(true);
54 + expect(ReactIs.isValidElementType(MemoComponent)).toEqual(true);
55 expect(ReactIs.isValidElementType(Context.Provider)).toEqual(true);
56 expect(ReactIs.isValidElementType(Context.Consumer)).toEqual(true);
57 expect(ReactIs.isValidElementType(React.createFactory('div'))).toEqual(
@@ -60,6 +62,7 @@ describe('ReactIs', () => {
62 true,
63 );
64 expect(ReactIs.isValidElementType(React.StrictMode)).toEqual(true);
65 + expect(ReactIs.isValidElementType(React.Suspense)).toEqual(true);
66
67 expect(ReactIs.isValidElementType(true)).toEqual(false);
68 expect(ReactIs.isValidElementType(123)).toEqual(false);
@@ -116,6 +119,7 @@ describe('ReactIs', () => {
119 expect(ReactIs.isElement(<React.Fragment />)).toBe(true);
120 expect(ReactIs.isElement(<React.unstable_ConcurrentMode />)).toBe(true);
121 expect(ReactIs.isElement(<React.StrictMode />)).toBe(true);
122 + expect(ReactIs.isElement(<React.Suspense />)).toBe(true);
123 });
124
125 it('should identify ref forwarding component', () => {
@@ -152,6 +156,14 @@ describe('ReactIs', () => {
156 expect(ReactIs.isMemo(Component)).toBe(false);
157 });
158
159 + it('should identify lazy', () => {
160 + const Component = () => React.createElement('div');
161 + const lazyComponent = React.lazy(() => Component);
162 + expect(ReactIs.typeOf(lazyComponent)).toBe(ReactIs.Lazy);
163 + expect(ReactIs.isLazy(lazyComponent)).toBe(true);
164 + expect(ReactIs.isLazy(Component)).toBe(false);
165 + });
166 +
167 it('should identify strict mode', () => {
168 expect(ReactIs.typeOf(<React.StrictMode />)).toBe(ReactIs.StrictMode);
169 expect(ReactIs.isStrictMode(<React.StrictMode />)).toBe(true);
@@ -160,6 +172,14 @@ describe('ReactIs', () => {
172 expect(ReactIs.isStrictMode(<div />)).toBe(false);
173 });
174
175 + it('should identify suspense', () => {
176 + expect(ReactIs.typeOf(<React.Suspense />)).toBe(ReactIs.Suspense);
177 + expect(ReactIs.isSuspense(<React.Suspense />)).toBe(true);
178 + expect(ReactIs.isSuspense({type: ReactIs.Suspense})).toBe(false);
179 + expect(ReactIs.isSuspense('React.Suspense')).toBe(false);
180 + expect(ReactIs.isSuspense(<div />)).toBe(false);
181 + });
182 +
183 it('should identify profile root', () => {
184 expect(
185 ReactIs.typeOf(<React.unstable_Profiler id="foo" onRender={jest.fn()} />),