react-server-dom-webpack 19.0.0-canary-48ec17b86-20240402 → 19.0.0-canary-7a2609eed-20240403
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/cjs/react-server-dom-webpack-client.browser.development.js +13 -5
- package/cjs/react-server-dom-webpack-client.edge.development.js +13 -5
- package/cjs/react-server-dom-webpack-client.node.development.js +13 -5
- package/cjs/react-server-dom-webpack-client.node.unbundled.development.js +13 -5
- package/cjs/react-server-dom-webpack-server.browser.development.js +74 -25
- package/cjs/react-server-dom-webpack-server.browser.production.js +73 -26
- package/cjs/react-server-dom-webpack-server.browser.production.min.js +46 -45
- package/cjs/react-server-dom-webpack-server.browser.production.min.js.map +1 -1
- package/cjs/react-server-dom-webpack-server.edge.development.js +74 -25
- package/cjs/react-server-dom-webpack-server.edge.production.js +73 -26
- package/cjs/react-server-dom-webpack-server.edge.production.min.js +32 -31
- package/cjs/react-server-dom-webpack-server.edge.production.min.js.map +1 -1
- package/cjs/react-server-dom-webpack-server.node.development.js +74 -25
- package/cjs/react-server-dom-webpack-server.node.production.js +73 -26
- package/cjs/react-server-dom-webpack-server.node.production.min.js +33 -31
- package/cjs/react-server-dom-webpack-server.node.production.min.js.map +1 -1
- package/cjs/react-server-dom-webpack-server.node.unbundled.development.js +74 -25
- package/cjs/react-server-dom-webpack-server.node.unbundled.production.js +73 -26
- package/cjs/react-server-dom-webpack-server.node.unbundled.production.min.js +33 -31
- package/cjs/react-server-dom-webpack-server.node.unbundled.production.min.js.map +1 -1
- package/package.json +3 -3
- package/umd/react-server-dom-webpack-client.browser.development.js +13 -5
- package/umd/react-server-dom-webpack-server.browser.development.js +74 -25
- package/umd/react-server-dom-webpack-server.browser.production.min.js +50 -50
@@ -411,7 +411,7 @@ function printWarning(level, format, args) {
|
|
411
411
|
// Please consider also adding to 'react-devtools-shared/src/backend/ReactSymbols'
|
412
412
|
// The Symbol used to tag the ReactElement-like types.
|
413
413
|
var REACT_ELEMENT_TYPE = Symbol.for('react.element');
|
414
|
-
var
|
414
|
+
var REACT_CONTEXT_TYPE = Symbol.for('react.context');
|
415
415
|
var REACT_FORWARD_REF_TYPE = Symbol.for('react.forward_ref');
|
416
416
|
var REACT_SUSPENSE_TYPE = Symbol.for('react.suspense');
|
417
417
|
var REACT_SUSPENSE_LIST_TYPE = Symbol.for('react.suspense_list');
|
@@ -1077,7 +1077,7 @@ function processReply(root, formFieldPrefix, temporaryReferences, resolve, rejec
|
|
1077
1077
|
}
|
1078
1078
|
|
1079
1079
|
{
|
1080
|
-
if (value.$$typeof === (
|
1080
|
+
if (value.$$typeof === (REACT_CONTEXT_TYPE )) {
|
1081
1081
|
error('React Context Providers cannot be passed to Server Functions from the Client.%s', describeObjectForErrorMessage(parent, key));
|
1082
1082
|
} else if (objectName(value) !== 'Object') {
|
1083
1083
|
error('Only plain objects can be passed to Server Functions from the Client. ' + '%s objects are not supported.%s', objectName(value), describeObjectForErrorMessage(parent, key));
|
@@ -1497,20 +1497,28 @@ function reportGlobalError(response, error) {
|
|
1497
1497
|
});
|
1498
1498
|
}
|
1499
1499
|
|
1500
|
+
function nullRefGetter() {
|
1501
|
+
{
|
1502
|
+
return null;
|
1503
|
+
}
|
1504
|
+
}
|
1505
|
+
|
1500
1506
|
function createElement(type, key, props) {
|
1501
1507
|
var element;
|
1502
1508
|
|
1503
1509
|
{
|
1510
|
+
// `ref` is non-enumerable in dev
|
1504
1511
|
element = {
|
1505
|
-
// This tag allows us to uniquely identify this as a React Element
|
1506
1512
|
$$typeof: REACT_ELEMENT_TYPE,
|
1507
1513
|
type: type,
|
1508
1514
|
key: key,
|
1509
|
-
ref: null,
|
1510
1515
|
props: props,
|
1511
|
-
// Record the component responsible for creating this element.
|
1512
1516
|
_owner: null
|
1513
1517
|
};
|
1518
|
+
Object.defineProperty(element, 'ref', {
|
1519
|
+
enumerable: false,
|
1520
|
+
get: nullRefGetter
|
1521
|
+
});
|
1514
1522
|
}
|
1515
1523
|
|
1516
1524
|
{
|
@@ -430,7 +430,7 @@ function printWarning(level, format, args) {
|
|
430
430
|
// Please consider also adding to 'react-devtools-shared/src/backend/ReactSymbols'
|
431
431
|
// The Symbol used to tag the ReactElement-like types.
|
432
432
|
var REACT_ELEMENT_TYPE = Symbol.for('react.element');
|
433
|
-
var
|
433
|
+
var REACT_CONTEXT_TYPE = Symbol.for('react.context');
|
434
434
|
var REACT_FORWARD_REF_TYPE = Symbol.for('react.forward_ref');
|
435
435
|
var REACT_SUSPENSE_TYPE = Symbol.for('react.suspense');
|
436
436
|
var REACT_SUSPENSE_LIST_TYPE = Symbol.for('react.suspense_list');
|
@@ -1096,7 +1096,7 @@ function processReply(root, formFieldPrefix, temporaryReferences, resolve, rejec
|
|
1096
1096
|
}
|
1097
1097
|
|
1098
1098
|
{
|
1099
|
-
if (value.$$typeof === (
|
1099
|
+
if (value.$$typeof === (REACT_CONTEXT_TYPE )) {
|
1100
1100
|
error('React Context Providers cannot be passed to Server Functions from the Client.%s', describeObjectForErrorMessage(parent, key));
|
1101
1101
|
} else if (objectName(value) !== 'Object') {
|
1102
1102
|
error('Only plain objects can be passed to Server Functions from the Client. ' + '%s objects are not supported.%s', objectName(value), describeObjectForErrorMessage(parent, key));
|
@@ -1750,20 +1750,28 @@ function reportGlobalError(response, error) {
|
|
1750
1750
|
});
|
1751
1751
|
}
|
1752
1752
|
|
1753
|
+
function nullRefGetter() {
|
1754
|
+
{
|
1755
|
+
return null;
|
1756
|
+
}
|
1757
|
+
}
|
1758
|
+
|
1753
1759
|
function createElement(type, key, props) {
|
1754
1760
|
var element;
|
1755
1761
|
|
1756
1762
|
{
|
1763
|
+
// `ref` is non-enumerable in dev
|
1757
1764
|
element = {
|
1758
|
-
// This tag allows us to uniquely identify this as a React Element
|
1759
1765
|
$$typeof: REACT_ELEMENT_TYPE,
|
1760
1766
|
type: type,
|
1761
1767
|
key: key,
|
1762
|
-
ref: null,
|
1763
1768
|
props: props,
|
1764
|
-
// Record the component responsible for creating this element.
|
1765
1769
|
_owner: null
|
1766
1770
|
};
|
1771
|
+
Object.defineProperty(element, 'ref', {
|
1772
|
+
enumerable: false,
|
1773
|
+
get: nullRefGetter
|
1774
|
+
});
|
1767
1775
|
}
|
1768
1776
|
|
1769
1777
|
{
|
@@ -431,7 +431,7 @@ function printWarning(level, format, args) {
|
|
431
431
|
// Please consider also adding to 'react-devtools-shared/src/backend/ReactSymbols'
|
432
432
|
// The Symbol used to tag the ReactElement-like types.
|
433
433
|
var REACT_ELEMENT_TYPE = Symbol.for('react.element');
|
434
|
-
var
|
434
|
+
var REACT_CONTEXT_TYPE = Symbol.for('react.context');
|
435
435
|
var REACT_FORWARD_REF_TYPE = Symbol.for('react.forward_ref');
|
436
436
|
var REACT_SUSPENSE_TYPE = Symbol.for('react.suspense');
|
437
437
|
var REACT_SUSPENSE_LIST_TYPE = Symbol.for('react.suspense_list');
|
@@ -1094,7 +1094,7 @@ function processReply(root, formFieldPrefix, temporaryReferences, resolve, rejec
|
|
1094
1094
|
}
|
1095
1095
|
|
1096
1096
|
{
|
1097
|
-
if (value.$$typeof === (
|
1097
|
+
if (value.$$typeof === (REACT_CONTEXT_TYPE )) {
|
1098
1098
|
error('React Context Providers cannot be passed to Server Functions from the Client.%s', describeObjectForErrorMessage(parent, key));
|
1099
1099
|
} else if (objectName(value) !== 'Object') {
|
1100
1100
|
error('Only plain objects can be passed to Server Functions from the Client. ' + '%s objects are not supported.%s', objectName(value), describeObjectForErrorMessage(parent, key));
|
@@ -1748,20 +1748,28 @@ function reportGlobalError(response, error) {
|
|
1748
1748
|
});
|
1749
1749
|
}
|
1750
1750
|
|
1751
|
+
function nullRefGetter() {
|
1752
|
+
{
|
1753
|
+
return null;
|
1754
|
+
}
|
1755
|
+
}
|
1756
|
+
|
1751
1757
|
function createElement(type, key, props) {
|
1752
1758
|
var element;
|
1753
1759
|
|
1754
1760
|
{
|
1761
|
+
// `ref` is non-enumerable in dev
|
1755
1762
|
element = {
|
1756
|
-
// This tag allows us to uniquely identify this as a React Element
|
1757
1763
|
$$typeof: REACT_ELEMENT_TYPE,
|
1758
1764
|
type: type,
|
1759
1765
|
key: key,
|
1760
|
-
ref: null,
|
1761
1766
|
props: props,
|
1762
|
-
// Record the component responsible for creating this element.
|
1763
1767
|
_owner: null
|
1764
1768
|
};
|
1769
|
+
Object.defineProperty(element, 'ref', {
|
1770
|
+
enumerable: false,
|
1771
|
+
get: nullRefGetter
|
1772
|
+
});
|
1765
1773
|
}
|
1766
1774
|
|
1767
1775
|
{
|
@@ -384,7 +384,7 @@ function printWarning(level, format, args) {
|
|
384
384
|
// Please consider also adding to 'react-devtools-shared/src/backend/ReactSymbols'
|
385
385
|
// The Symbol used to tag the ReactElement-like types.
|
386
386
|
var REACT_ELEMENT_TYPE = Symbol.for('react.element');
|
387
|
-
var
|
387
|
+
var REACT_CONTEXT_TYPE = Symbol.for('react.context');
|
388
388
|
var REACT_FORWARD_REF_TYPE = Symbol.for('react.forward_ref');
|
389
389
|
var REACT_SUSPENSE_TYPE = Symbol.for('react.suspense');
|
390
390
|
var REACT_SUSPENSE_LIST_TYPE = Symbol.for('react.suspense_list');
|
@@ -1047,7 +1047,7 @@ function processReply(root, formFieldPrefix, temporaryReferences, resolve, rejec
|
|
1047
1047
|
}
|
1048
1048
|
|
1049
1049
|
{
|
1050
|
-
if (value.$$typeof === (
|
1050
|
+
if (value.$$typeof === (REACT_CONTEXT_TYPE )) {
|
1051
1051
|
error('React Context Providers cannot be passed to Server Functions from the Client.%s', describeObjectForErrorMessage(parent, key));
|
1052
1052
|
} else if (objectName(value) !== 'Object') {
|
1053
1053
|
error('Only plain objects can be passed to Server Functions from the Client. ' + '%s objects are not supported.%s', objectName(value), describeObjectForErrorMessage(parent, key));
|
@@ -1701,20 +1701,28 @@ function reportGlobalError(response, error) {
|
|
1701
1701
|
});
|
1702
1702
|
}
|
1703
1703
|
|
1704
|
+
function nullRefGetter() {
|
1705
|
+
{
|
1706
|
+
return null;
|
1707
|
+
}
|
1708
|
+
}
|
1709
|
+
|
1704
1710
|
function createElement(type, key, props) {
|
1705
1711
|
var element;
|
1706
1712
|
|
1707
1713
|
{
|
1714
|
+
// `ref` is non-enumerable in dev
|
1708
1715
|
element = {
|
1709
|
-
// This tag allows us to uniquely identify this as a React Element
|
1710
1716
|
$$typeof: REACT_ELEMENT_TYPE,
|
1711
1717
|
type: type,
|
1712
1718
|
key: key,
|
1713
|
-
ref: null,
|
1714
1719
|
props: props,
|
1715
|
-
// Record the component responsible for creating this element.
|
1716
1720
|
_owner: null
|
1717
1721
|
};
|
1722
|
+
Object.defineProperty(element, 'ref', {
|
1723
|
+
enumerable: false,
|
1724
|
+
get: nullRefGetter
|
1725
|
+
});
|
1718
1726
|
}
|
1719
1727
|
|
1720
1728
|
{
|
@@ -1034,10 +1034,6 @@ function use(usable) {
|
|
1034
1034
|
}
|
1035
1035
|
}
|
1036
1036
|
|
1037
|
-
function createSignal() {
|
1038
|
-
return new AbortController().signal;
|
1039
|
-
}
|
1040
|
-
|
1041
1037
|
function resolveCache() {
|
1042
1038
|
var request = resolveRequest();
|
1043
1039
|
|
@@ -1049,17 +1045,6 @@ function resolveCache() {
|
|
1049
1045
|
}
|
1050
1046
|
|
1051
1047
|
var DefaultCacheDispatcher = {
|
1052
|
-
getCacheSignal: function () {
|
1053
|
-
var cache = resolveCache();
|
1054
|
-
var entry = cache.get(createSignal);
|
1055
|
-
|
1056
|
-
if (entry === undefined) {
|
1057
|
-
entry = createSignal();
|
1058
|
-
cache.set(createSignal, entry);
|
1059
|
-
}
|
1060
|
-
|
1061
|
-
return entry;
|
1062
|
-
},
|
1063
1048
|
getCacheForType: function (resourceType) {
|
1064
1049
|
var cache = resolveCache();
|
1065
1050
|
var entry = cache.get(resourceType);
|
@@ -1736,15 +1721,68 @@ function renderFragment(request, task, children) {
|
|
1736
1721
|
}
|
1737
1722
|
}
|
1738
1723
|
|
1739
|
-
{
|
1740
|
-
|
1741
|
-
|
1724
|
+
if (task.keyPath !== null) {
|
1725
|
+
// We have a Server Component that specifies a key but we're now splitting
|
1726
|
+
// the tree using a fragment.
|
1727
|
+
var fragment = [REACT_ELEMENT_TYPE, REACT_FRAGMENT_TYPE, task.keyPath, {
|
1728
|
+
children: children
|
1729
|
+
}];
|
1730
|
+
|
1731
|
+
if (!task.implicitSlot) {
|
1732
|
+
// If this was keyed inside a set. I.e. the outer Server Component was keyed
|
1733
|
+
// then we need to handle reorders of the whole set. To do this we need to wrap
|
1734
|
+
// this array in a keyed Fragment.
|
1735
|
+
return fragment;
|
1736
|
+
} // If the outer Server Component was implicit but then an inner one had a key
|
1737
|
+
// we don't actually need to be able to move the whole set around. It'll always be
|
1738
|
+
// in an implicit slot. The key only exists to be able to reset the state of the
|
1739
|
+
// children. We could achieve the same effect by passing on the keyPath to the next
|
1740
|
+
// set of components inside the fragment. This would also allow a keyless fragment
|
1741
|
+
// reconcile against a single child.
|
1742
|
+
// Unfortunately because of JSON.stringify, we can't call the recursive loop for
|
1743
|
+
// each child within this context because we can't return a set with already resolved
|
1744
|
+
// values. E.g. a string would get double encoded. Returning would pop the context.
|
1745
|
+
// So instead, we wrap it with an unkeyed fragment and inner keyed fragment.
|
1746
|
+
|
1747
|
+
|
1748
|
+
return [fragment];
|
1749
|
+
} // Since we're yielding here, that implicitly resets the keyPath context on the
|
1750
|
+
// way up. Which is what we want since we've consumed it. If this changes to
|
1751
|
+
// be recursive serialization, we need to reset the keyPath and implicitSlot,
|
1752
|
+
// before recursing here.
|
1753
|
+
|
1754
|
+
|
1755
|
+
return children;
|
1742
1756
|
}
|
1743
1757
|
|
1744
1758
|
function renderClientElement(task, type, key, props) {
|
1745
|
-
|
1746
|
-
|
1747
|
-
|
1759
|
+
// the keys of any Server Components which are not serialized.
|
1760
|
+
|
1761
|
+
|
1762
|
+
var keyPath = task.keyPath;
|
1763
|
+
|
1764
|
+
if (key === null) {
|
1765
|
+
key = keyPath;
|
1766
|
+
} else if (keyPath !== null) {
|
1767
|
+
key = keyPath + ',' + key;
|
1768
|
+
}
|
1769
|
+
|
1770
|
+
var element = [REACT_ELEMENT_TYPE, type, key, props];
|
1771
|
+
|
1772
|
+
if (task.implicitSlot && key !== null) {
|
1773
|
+
// The root Server Component had no key so it was in an implicit slot.
|
1774
|
+
// If we had a key lower, it would end up in that slot with an explicit key.
|
1775
|
+
// We wrap the element in a fragment to give it an implicit key slot with
|
1776
|
+
// an inner explicit key.
|
1777
|
+
return [element];
|
1778
|
+
} // Since we're yielding here, that implicitly resets the keyPath context on the
|
1779
|
+
// way up. Which is what we want since we've consumed it. If this changes to
|
1780
|
+
// be recursive serialization, we need to reset the keyPath and implicitSlot,
|
1781
|
+
// before recursing here. We also need to reset it once we render into an array
|
1782
|
+
// or anything else too which we also get implicitly.
|
1783
|
+
|
1784
|
+
|
1785
|
+
return element;
|
1748
1786
|
} // The chunk ID we're currently rendering that we can assign debug data to.
|
1749
1787
|
|
1750
1788
|
|
@@ -1863,7 +1901,7 @@ function createTask(request, model, keyPath, implicitSlot, abortSet) {
|
|
1863
1901
|
if (typeof model === 'object' && model !== null) {
|
1864
1902
|
// If we're about to write this into a new task we can assign it an ID early so that
|
1865
1903
|
// any other references can refer to the value we're about to write.
|
1866
|
-
{
|
1904
|
+
if ((keyPath !== null || implicitSlot)) ; else {
|
1867
1905
|
request.writtenObjects.set(model, id);
|
1868
1906
|
}
|
1869
1907
|
}
|
@@ -2194,7 +2232,7 @@ function renderModelDestructive(request, task, parent, parentPropertyName, value
|
|
2194
2232
|
var _existingId = _writtenObjects.get(value);
|
2195
2233
|
|
2196
2234
|
if (_existingId !== undefined) {
|
2197
|
-
if (modelRoot === value) {
|
2235
|
+
if ((task.keyPath !== null || task.implicitSlot)) ; else if (modelRoot === value) {
|
2198
2236
|
// This is the ID we're currently emitting so we need to write it
|
2199
2237
|
// once but if we discover it again, we refer to it by id.
|
2200
2238
|
modelRoot = null;
|
@@ -2246,7 +2284,11 @@ function renderModelDestructive(request, task, parent, parentPropertyName, value
|
|
2246
2284
|
var ref;
|
2247
2285
|
|
2248
2286
|
{
|
2249
|
-
|
2287
|
+
// TODO: This is a temporary, intermediate step. Once the feature
|
2288
|
+
// flag is removed, we should get the ref off the props object right
|
2289
|
+
// before using it.
|
2290
|
+
var refProp = props.ref;
|
2291
|
+
ref = refProp !== undefined ? refProp : null;
|
2250
2292
|
} // Attempt to render the Server Component.
|
2251
2293
|
|
2252
2294
|
|
@@ -2295,7 +2337,14 @@ function renderModelDestructive(request, task, parent, parentPropertyName, value
|
|
2295
2337
|
|
2296
2338
|
if (typeof value.then === 'function') {
|
2297
2339
|
if (existingId !== undefined) {
|
2298
|
-
if (
|
2340
|
+
if ((task.keyPath !== null || task.implicitSlot)) {
|
2341
|
+
// If we're in some kind of context we can't reuse the result of this render or
|
2342
|
+
// previous renders of this element. We only reuse Promises if they're not wrapped
|
2343
|
+
// by another Server Component.
|
2344
|
+
var _promiseId = serializeThenable(request, task, value);
|
2345
|
+
|
2346
|
+
return serializePromiseID(_promiseId);
|
2347
|
+
} else if (modelRoot === value) {
|
2299
2348
|
// This is the ID we're currently emitting so we need to write it
|
2300
2349
|
// once but if we discover it again, we refer to it by id.
|
2301
2350
|
modelRoot = null;
|
@@ -992,10 +992,6 @@ function use(usable) {
|
|
992
992
|
}
|
993
993
|
}
|
994
994
|
|
995
|
-
function createSignal() {
|
996
|
-
return new AbortController().signal;
|
997
|
-
}
|
998
|
-
|
999
995
|
function resolveCache() {
|
1000
996
|
const request = resolveRequest();
|
1001
997
|
|
@@ -1007,18 +1003,6 @@ function resolveCache() {
|
|
1007
1003
|
}
|
1008
1004
|
|
1009
1005
|
const DefaultCacheDispatcher = {
|
1010
|
-
getCacheSignal() {
|
1011
|
-
const cache = resolveCache();
|
1012
|
-
let entry = cache.get(createSignal);
|
1013
|
-
|
1014
|
-
if (entry === undefined) {
|
1015
|
-
entry = createSignal();
|
1016
|
-
cache.set(createSignal, entry);
|
1017
|
-
}
|
1018
|
-
|
1019
|
-
return entry;
|
1020
|
-
},
|
1021
|
-
|
1022
1006
|
getCacheForType(resourceType) {
|
1023
1007
|
const cache = resolveCache();
|
1024
1008
|
let entry = cache.get(resourceType);
|
@@ -1512,15 +1496,68 @@ function renderFunctionComponent(request, task, key, Component, props) {
|
|
1512
1496
|
|
1513
1497
|
function renderFragment(request, task, children) {
|
1514
1498
|
|
1515
|
-
{
|
1516
|
-
|
1517
|
-
|
1499
|
+
if (task.keyPath !== null) {
|
1500
|
+
// We have a Server Component that specifies a key but we're now splitting
|
1501
|
+
// the tree using a fragment.
|
1502
|
+
const fragment = [REACT_ELEMENT_TYPE, REACT_FRAGMENT_TYPE, task.keyPath, {
|
1503
|
+
children
|
1504
|
+
}];
|
1505
|
+
|
1506
|
+
if (!task.implicitSlot) {
|
1507
|
+
// If this was keyed inside a set. I.e. the outer Server Component was keyed
|
1508
|
+
// then we need to handle reorders of the whole set. To do this we need to wrap
|
1509
|
+
// this array in a keyed Fragment.
|
1510
|
+
return fragment;
|
1511
|
+
} // If the outer Server Component was implicit but then an inner one had a key
|
1512
|
+
// we don't actually need to be able to move the whole set around. It'll always be
|
1513
|
+
// in an implicit slot. The key only exists to be able to reset the state of the
|
1514
|
+
// children. We could achieve the same effect by passing on the keyPath to the next
|
1515
|
+
// set of components inside the fragment. This would also allow a keyless fragment
|
1516
|
+
// reconcile against a single child.
|
1517
|
+
// Unfortunately because of JSON.stringify, we can't call the recursive loop for
|
1518
|
+
// each child within this context because we can't return a set with already resolved
|
1519
|
+
// values. E.g. a string would get double encoded. Returning would pop the context.
|
1520
|
+
// So instead, we wrap it with an unkeyed fragment and inner keyed fragment.
|
1521
|
+
|
1522
|
+
|
1523
|
+
return [fragment];
|
1524
|
+
} // Since we're yielding here, that implicitly resets the keyPath context on the
|
1525
|
+
// way up. Which is what we want since we've consumed it. If this changes to
|
1526
|
+
// be recursive serialization, we need to reset the keyPath and implicitSlot,
|
1527
|
+
// before recursing here.
|
1528
|
+
|
1529
|
+
|
1530
|
+
return children;
|
1518
1531
|
}
|
1519
1532
|
|
1520
1533
|
function renderClientElement(task, type, key, props) {
|
1521
|
-
|
1522
|
-
|
1523
|
-
|
1534
|
+
// the keys of any Server Components which are not serialized.
|
1535
|
+
|
1536
|
+
|
1537
|
+
const keyPath = task.keyPath;
|
1538
|
+
|
1539
|
+
if (key === null) {
|
1540
|
+
key = keyPath;
|
1541
|
+
} else if (keyPath !== null) {
|
1542
|
+
key = keyPath + ',' + key;
|
1543
|
+
}
|
1544
|
+
|
1545
|
+
const element = [REACT_ELEMENT_TYPE, type, key, props];
|
1546
|
+
|
1547
|
+
if (task.implicitSlot && key !== null) {
|
1548
|
+
// The root Server Component had no key so it was in an implicit slot.
|
1549
|
+
// If we had a key lower, it would end up in that slot with an explicit key.
|
1550
|
+
// We wrap the element in a fragment to give it an implicit key slot with
|
1551
|
+
// an inner explicit key.
|
1552
|
+
return [element];
|
1553
|
+
} // Since we're yielding here, that implicitly resets the keyPath context on the
|
1554
|
+
// way up. Which is what we want since we've consumed it. If this changes to
|
1555
|
+
// be recursive serialization, we need to reset the keyPath and implicitSlot,
|
1556
|
+
// before recursing here. We also need to reset it once we render into an array
|
1557
|
+
// or anything else too which we also get implicitly.
|
1558
|
+
|
1559
|
+
|
1560
|
+
return element;
|
1524
1561
|
} // The chunk ID we're currently rendering that we can assign debug data to.
|
1525
1562
|
|
1526
1563
|
|
@@ -1612,7 +1649,7 @@ function createTask(request, model, keyPath, implicitSlot, abortSet) {
|
|
1612
1649
|
if (typeof model === 'object' && model !== null) {
|
1613
1650
|
// If we're about to write this into a new task we can assign it an ID early so that
|
1614
1651
|
// any other references can refer to the value we're about to write.
|
1615
|
-
{
|
1652
|
+
if ((keyPath !== null || implicitSlot)) ; else {
|
1616
1653
|
request.writtenObjects.set(model, id);
|
1617
1654
|
}
|
1618
1655
|
}
|
@@ -1921,7 +1958,7 @@ function renderModelDestructive(request, task, parent, parentPropertyName, value
|
|
1921
1958
|
const existingId = writtenObjects.get(value);
|
1922
1959
|
|
1923
1960
|
if (existingId !== undefined) {
|
1924
|
-
if (modelRoot === value) {
|
1961
|
+
if ((task.keyPath !== null || task.implicitSlot)) ; else if (modelRoot === value) {
|
1925
1962
|
// This is the ID we're currently emitting so we need to write it
|
1926
1963
|
// once but if we discover it again, we refer to it by id.
|
1927
1964
|
modelRoot = null;
|
@@ -1956,7 +1993,11 @@ function renderModelDestructive(request, task, parent, parentPropertyName, value
|
|
1956
1993
|
let ref;
|
1957
1994
|
|
1958
1995
|
{
|
1959
|
-
|
1996
|
+
// TODO: This is a temporary, intermediate step. Once the feature
|
1997
|
+
// flag is removed, we should get the ref off the props object right
|
1998
|
+
// before using it.
|
1999
|
+
const refProp = props.ref;
|
2000
|
+
ref = refProp !== undefined ? refProp : null;
|
1960
2001
|
} // Attempt to render the Server Component.
|
1961
2002
|
|
1962
2003
|
|
@@ -1987,7 +2028,13 @@ function renderModelDestructive(request, task, parent, parentPropertyName, value
|
|
1987
2028
|
|
1988
2029
|
if (typeof value.then === 'function') {
|
1989
2030
|
if (existingId !== undefined) {
|
1990
|
-
if (
|
2031
|
+
if ((task.keyPath !== null || task.implicitSlot)) {
|
2032
|
+
// If we're in some kind of context we can't reuse the result of this render or
|
2033
|
+
// previous renders of this element. We only reuse Promises if they're not wrapped
|
2034
|
+
// by another Server Component.
|
2035
|
+
const promiseId = serializeThenable(request, task, value);
|
2036
|
+
return serializePromiseID(promiseId);
|
2037
|
+
} else if (modelRoot === value) {
|
1991
2038
|
// This is the ID we're currently emitting so we need to write it
|
1992
2039
|
// once but if we discover it again, we refer to it by id.
|
1993
2040
|
modelRoot = null;
|