@@ -38,6 +38,10 @@ import {
38
38
stringToPrecomputedChunk ,
39
39
clonePrecomputedChunk ,
40
40
} from 'react-server/src/ReactServerStreamConfig' ;
41
+ import {
42
+ resolveResources ,
43
+ pingRequest ,
44
+ } from 'react-server/src/ReactFizzResources' ;
41
45
42
46
import isAttributeNameSafe from '../shared/isAttributeNameSafe' ;
43
47
import isUnitlessNumber from '../shared/isUnitlessNumber' ;
@@ -79,30 +83,15 @@ import {
79
83
import ReactDOMSharedInternals from 'shared/ReactDOMSharedInternals' ;
80
84
const ReactDOMCurrentDispatcher = ReactDOMSharedInternals . Dispatcher ;
81
85
82
- const ReactDOMServerDispatcher = enableFloat
83
- ? {
84
- prefetchDNS,
85
- preconnect,
86
- preload,
87
- preinit,
88
- }
89
- : { } ;
90
-
91
- let currentResources : null | Resources = null ;
92
- const currentResourcesStack = [ ] ;
93
-
94
- export function prepareToRender ( resources : Resources ) : mixed {
95
- currentResourcesStack . push ( currentResources ) ;
96
- currentResources = resources ;
86
+ const ReactDOMServerDispatcher = {
87
+ prefetchDNS,
88
+ preconnect,
89
+ preload,
90
+ preinit,
91
+ } ;
97
92
98
- const previousHostDispatcher = ReactDOMCurrentDispatcher . current ;
93
+ export function prepareHostDispatcher ( ) {
99
94
ReactDOMCurrentDispatcher . current = ReactDOMServerDispatcher ;
100
- return previousHostDispatcher ;
101
- }
102
-
103
- export function cleanupAfterRender ( previousDispatcher : mixed ) {
104
- currentResources = currentResourcesStack . pop ( ) ;
105
- ReactDOMCurrentDispatcher . current = previousDispatcher ;
106
95
}
107
96
108
97
// Used to distinguish these contexts from ones used in other renderers.
@@ -4804,16 +4793,18 @@ function getResourceKey(as: string, href: string): string {
4804
4793
}
4805
4794
4806
4795
export function prefetchDNS ( href : string , options ?: mixed ) {
4807
- if ( ! currentResources ) {
4808
- // While we expect that preconnect calls are primarily going to be observed
4809
- // during render because effects and events don't run on the server it is
4810
- // still possible that these get called in module scope. This is valid on
4811
- // the client since there is still a document to interact with but on the
4812
- // server we need a request to associate the call to. Because of this we
4813
- // simply return and do not warn.
4796
+ if ( ! enableFloat ) {
4797
+ return ;
4798
+ }
4799
+ const resources = resolveResources ( ) ;
4800
+ if ( ! resources ) {
4801
+ // In async contexts we can sometimes resolve resources from AsyncLocalStorage. If we can't we can also
4802
+ // possibly get them from the stack if we are not in an async context. Since we were not able to resolve
4803
+ // the resources for this call in either case we opt to do nothing. We can consider making this a warning
4804
+ // but there may be times where calling a function outside of render is intentional (i.e. to warm up data
4805
+ // fetching) and we don't want to warn in those cases.
4814
4806
return ;
4815
4807
}
4816
- const resources = currentResources ;
4817
4808
if ( __DEV__ ) {
4818
4809
if ( typeof href !== 'string' || ! href ) {
4819
4810
console . error (
@@ -4858,17 +4849,19 @@ export function prefetchDNS(href: string, options?: mixed) {
4858
4849
}
4859
4850
}
4860
4851
4861
- export function preconnect ( href : string , options ?: { crossOrigin ?: string } ) {
4862
- if ( ! currentResources ) {
4863
- // While we expect that preconnect calls are primarily going to be observed
4864
- // during render because effects and events don't run on the server it is
4865
- // still possible that these get called in module scope. This is valid on
4866
- // the client since there is still a document to interact with but on the
4867
- // server we need a request to associate the call to. Because of this we
4868
- // simply return and do not warn.
4852
+ export function preconnect ( href : string , options ?: ?{ crossOrigin ?: string } ) {
4853
+ if ( ! enableFloat ) {
4854
+ return ;
4855
+ }
4856
+ const resources = resolveResources ( ) ;
4857
+ if ( ! resources ) {
4858
+ // In async contexts we can sometimes resolve resources from AsyncLocalStorage. If we can't we can also
4859
+ // possibly get them from the stack if we are not in an async context. Since we were not able to resolve
4860
+ // the resources for this call in either case we opt to do nothing. We can consider making this a warning
4861
+ // but there may be times where calling a function outside of render is intentional (i.e. to warm up data
4862
+ // fetching) and we don't want to warn in those cases.
4869
4863
return;
4870
4864
}
4871
- const resources = currentResources ;
4872
4865
if ( __DEV__ ) {
4873
4866
if ( typeof href !== 'string' || ! href ) {
4874
4867
console . error (
@@ -4917,24 +4910,25 @@ export function preconnect(href: string, options?: {crossOrigin?: string}) {
4917
4910
}
4918
4911
}
4919
4912
4920
- type PreloadAs = 'style' | 'font' | 'script' ;
4921
4913
type PreloadOptions = {
4922
- as : PreloadAs ,
4914
+ as : string ,
4923
4915
crossOrigin ?: string ,
4924
4916
integrity ?: string ,
4925
4917
type ?: string ,
4926
4918
} ;
4927
4919
export function preload ( href : string , options : PreloadOptions ) {
4928
- if ( ! currentResources ) {
4929
- // While we expect that preload calls are primarily going to be observed
4930
- // during render because effects and events don't run on the server it is
4931
- // still possible that these get called in module scope. This is valid on
4932
- // the client since there is still a document to interact with but on the
4933
- // server we need a request to associate the call to. Because of this we
4934
- // simply return and do not warn.
4920
+ if ( ! enableFloat ) {
4921
+ return ;
4922
+ }
4923
+ const resources = resolveResources ( ) ;
4924
+ if ( ! resources ) {
4925
+ // In async contexts we can sometimes resolve resources from AsyncLocalStorage. If we can't we can also
4926
+ // possibly get them from the stack if we are not in an async context. Since we were not able to resolve
4927
+ // the resources for this call in either case we opt to do nothing. We can consider making this a warning
4928
+ // but there may be times where calling a function outside of render is intentional (i.e. to warm up data
4929
+ // fetching) and we don't want to warn in those cases.
4935
4930
return ;
4936
4931
}
4937
- const resources = currentResources ;
4938
4932
if ( __DEV__ ) {
4939
4933
if ( typeof href !== 'string' || ! href ) {
4940
4934
console . error (
@@ -5055,27 +5049,30 @@ export function preload(href: string, options: PreloadOptions) {
5055
5049
resources. explicitOtherPreloads . add ( resource ) ;
5056
5050
}
5057
5051
}
5052
+ pingRequest ( ) ;
5058
5053
}
5059
5054
}
5060
5055
5061
- type PreinitAs = 'style' | 'script' ;
5062
5056
type PreinitOptions = {
5063
- as : PreinitAs ,
5057
+ as : string ,
5064
5058
precedence ?: string ,
5065
5059
crossOrigin ?: string ,
5066
5060
integrity ?: string ,
5067
5061
} ;
5068
5062
export function preinit ( href : string , options : PreinitOptions ) : void {
5069
- if ( ! currentResources ) {
5070
- // While we expect that preinit calls are primarily going to be observed
5071
- // during render because effects and events don't run on the server it is
5072
- // still possible that these get called in module scope. This is valid on
5073
- // the client since there is still a document to interact with but on the
5074
- // server we need a request to associate the call to. Because of this we
5075
- // simply return and do not warn.
5063
+ if ( ! enableFloat ) {
5064
+ return ;
5065
+ }
5066
+ const resources = resolveResources ( ) ;
5067
+ if ( ! resources ) {
5068
+ // In async contexts we can sometimes resolve resources from AsyncLocalStorage. If we can't we can also
5069
+ // possibly get them from the stack if we are not in an async context. Since we were not able to resolve
5070
+ // the resources for this call in either case we opt to do nothing. We can consider making this a warning
5071
+ // but there may be times where calling a function outside of render is intentional (i.e. to warm up data
5072
+ // fetching) and we don't want to warn in those cases.
5076
5073
return;
5077
5074
}
5078
- preinitImpl ( currentResources , href, options) ;
5075
+ preinitImpl ( resources , href , options ) ;
5079
5076
}
5080
5077
5081
5078
// On the server, preinit may be called outside of render when sending an
@@ -5297,7 +5294,7 @@ function preinitImpl(
5297
5294
5298
5295
function preloadPropsFromPreloadOptions (
5299
5296
href : string ,
5300
- as : PreloadAs ,
5297
+ as : string ,
5301
5298
options : PreloadOptions ,
5302
5299
) : PreloadProps {
5303
5300
return {
0 commit comments