Skip to content

Commit 4809325

Browse files
committed
refactor(hydration): move fragment to seaprate function + skip normalization in optimized mode
1 parent 3357ff4 commit 4809325

File tree

1 file changed

+41
-28
lines changed

1 file changed

+41
-28
lines changed

packages/runtime-core/src/hydration.ts

+41-28
Original file line numberDiff line numberDiff line change
@@ -39,7 +39,8 @@ export function createHydrationFunctions({
3939
const hydrateNode = (
4040
node: Node,
4141
vnode: VNode,
42-
parentComponent: ComponentInternalInstance | null = null
42+
parentComponent: ComponentInternalInstance | null = null,
43+
optimized = false
4344
): Node | null => {
4445
const { type, shapeFlag } = vnode
4546
vnode.el = node
@@ -49,18 +50,15 @@ export function createHydrationFunctions({
4950
case Static:
5051
return node.nextSibling
5152
case Fragment:
52-
const parent = node.parentNode!
53-
parent.insertBefore((vnode.el = createText('')), node)
54-
const next = hydrateChildren(
55-
node,
56-
vnode.children as VNode[],
57-
parentComponent
58-
)
59-
parent.insertBefore((vnode.anchor = createText('')), next)
60-
return next
53+
return hydrateFragment(node, vnode, parentComponent, optimized)
6154
default:
6255
if (shapeFlag & ShapeFlags.ELEMENT) {
63-
return hydrateElement(node as Element, vnode, parentComponent)
56+
return hydrateElement(
57+
node as Element,
58+
vnode,
59+
parentComponent,
60+
optimized
61+
)
6462
} else if (shapeFlag & ShapeFlags.COMPONENT) {
6563
// when setting up the render effect, if the initial vnode already
6664
// has .el set, the component will perform hydration instead of mount
@@ -69,7 +67,7 @@ export function createHydrationFunctions({
6967
const subTree = vnode.component!.subTree
7068
return (subTree.anchor || subTree.el).nextSibling
7169
} else if (shapeFlag & ShapeFlags.PORTAL) {
72-
hydratePortal(vnode, parentComponent)
70+
hydratePortal(vnode, parentComponent, optimized)
7371
return node.nextSibling
7472
} else if (__FEATURE_SUSPENSE__ && shapeFlag & ShapeFlags.SUSPENSE) {
7573
// TODO Suspense
@@ -83,7 +81,8 @@ export function createHydrationFunctions({
8381
const hydrateElement = (
8482
el: Element,
8583
vnode: VNode,
86-
parentComponent: ComponentInternalInstance | null
84+
parentComponent: ComponentInternalInstance | null,
85+
optimized: boolean
8786
) => {
8887
const { props, patchFlag } = vnode
8988
// skip props & children if this is hoisted static nodes
@@ -123,8 +122,9 @@ export function createHydrationFunctions({
123122
) {
124123
hydrateChildren(
125124
el.firstChild,
126-
vnode.children as VNode[],
127-
parentComponent
125+
vnode,
126+
parentComponent,
127+
optimized || vnode.dynamicChildren !== null
128128
)
129129
}
130130
}
@@ -133,32 +133,45 @@ export function createHydrationFunctions({
133133

134134
const hydrateChildren = (
135135
node: Node | null,
136-
vnodes: VNode[],
137-
parentComponent: ComponentInternalInstance | null
136+
vnode: VNode,
137+
parentComponent: ComponentInternalInstance | null,
138+
optimized: boolean
138139
): Node | null => {
139-
for (let i = 0; node != null && i < vnodes.length; i++) {
140-
// TODO can skip normalizeVNode in optimized mode
141-
// (need hint on rendered markup?)
142-
const vnode = (vnodes[i] = normalizeVNode(vnodes[i]))
143-
node = hydrateNode(node, vnode, parentComponent)
140+
const children = vnode.children as VNode[]
141+
optimized = optimized || vnode.dynamicChildren !== null
142+
for (let i = 0; node != null && i < children.length; i++) {
143+
const vnode = optimized
144+
? children[i]
145+
: (children[i] = normalizeVNode(children[i]))
146+
node = hydrateNode(node, vnode, parentComponent, optimized)
144147
}
145148
return node
146149
}
147150

151+
const hydrateFragment = (
152+
node: Node,
153+
vnode: VNode,
154+
parentComponent: ComponentInternalInstance | null,
155+
optimized: boolean
156+
) => {
157+
const parent = node.parentNode!
158+
parent.insertBefore((vnode.el = createText('')), node)
159+
const next = hydrateChildren(node, vnode, parentComponent, optimized)
160+
parent.insertBefore((vnode.anchor = createText('')), next)
161+
return next
162+
}
163+
148164
const hydratePortal = (
149165
vnode: VNode,
150-
parentComponent: ComponentInternalInstance | null
166+
parentComponent: ComponentInternalInstance | null,
167+
optimized: boolean
151168
) => {
152169
const targetSelector = vnode.props && vnode.props.target
153170
const target = (vnode.target = isString(targetSelector)
154171
? document.querySelector(targetSelector)
155172
: targetSelector)
156173
if (target != null && vnode.shapeFlag & ShapeFlags.ARRAY_CHILDREN) {
157-
hydrateChildren(
158-
target.firstChild,
159-
vnode.children as VNode[],
160-
parentComponent
161-
)
174+
hydrateChildren(target.firstChild, vnode, parentComponent, optimized)
162175
}
163176
}
164177

0 commit comments

Comments
 (0)