1
+ /* eslint-disable no-underscore-dangle */
1
2
import React from 'react' ;
2
3
import configuration from '../configuration' ;
3
4
import { enterHotUpdate } from '../global/generation' ;
@@ -6,38 +7,77 @@ import { resolveType } from './resolver';
6
7
7
8
const lazyConstructor = '_ctor' ;
8
9
10
+ const getLazyConstructor = target => {
11
+ // React 16
12
+ if ( target [ lazyConstructor ] ) {
13
+ return target [ lazyConstructor ] ;
14
+ }
15
+
16
+ // React 17
17
+ if ( target . _payload ) {
18
+ return target . _payload . _result ;
19
+ }
20
+ return null ;
21
+ } ;
22
+
23
+ const setLazyConstructor = ( target , replacement ) => {
24
+ replacement . isPatchedByReactHotLoader = true ;
25
+
26
+ // React 16
27
+ if ( target [ lazyConstructor ] ) {
28
+ target [ lazyConstructor ] = replacement ;
29
+ }
30
+ // React 17
31
+ else if ( target . _payload ) {
32
+ target . _payload . _hotUpdated = true ;
33
+ target . _payload . _result = replacement ;
34
+ } else {
35
+ console . error ( 'could not update lazy component' ) ;
36
+ }
37
+ } ;
38
+
39
+ const patched = fn => {
40
+ fn . isPatchedByReactHotLoader = true ;
41
+ return fn ;
42
+ } ;
43
+
9
44
const patchLazyConstructor = target => {
10
- if ( ! configuration . trackTailUpdates && ! target [ lazyConstructor ] . isPatchedByReactHotLoader ) {
11
- const ctor = target [ lazyConstructor ] ;
12
- target [ lazyConstructor ] = ( ) =>
45
+ if ( configuration . wrapLazy && ! getLazyConstructor ( target ) . isPatchedByReactHotLoader ) {
46
+ const ctor = getLazyConstructor ( target ) ;
47
+ setLazyConstructor ( target , ( ) =>
13
48
ctor ( ) . then ( m => {
14
49
const C = resolveType ( m . default ) ;
15
50
// chunks has been updated - new hot loader process is taking a place
16
51
enterHotUpdate ( ) ;
17
52
if ( ! React . forwardRef ) {
18
53
return {
19
- default : props => (
54
+ default : patched ( props => (
20
55
< AppContainer >
21
56
< C { ...props } />
22
57
</ AppContainer >
23
- ) ,
58
+ ) ) ,
24
59
} ;
25
60
}
26
61
return {
27
- default : React . forwardRef ( ( props , ref ) => (
28
- < AppContainer >
29
- < C { ...props } ref = { ref } />
30
- </ AppContainer >
31
- ) ) ,
62
+ default : patched (
63
+ // eslint-disable-next-line prefer-arrow-callback
64
+ React . forwardRef ( function HotLoaderLazyWrapper ( props , ref ) {
65
+ return (
66
+ < AppContainer >
67
+ < C { ...props } ref = { ref } />
68
+ </ AppContainer >
69
+ ) ;
70
+ } ) ,
71
+ ) ,
32
72
} ;
33
- } ) ;
34
- target [ lazyConstructor ] . isPatchedByReactHotLoader = true ;
73
+ } ) ,
74
+ ) ;
35
75
}
36
76
} ;
37
77
38
78
export const updateLazy = ( target , type ) => {
39
- const ctor = type [ lazyConstructor ] ;
40
- if ( target [ lazyConstructor ] !== type [ lazyConstructor ] ) {
79
+ const ctor = getLazyConstructor ( type ) ;
80
+ if ( getLazyConstructor ( target ) !== ctor ) {
41
81
// just execute `import` and RHL.register will do the job
42
82
ctor ( ) ;
43
83
}
0 commit comments