Просмотр исходного кода

fix(Suspense): properly fix #6416

previous fix caused regressions in nuxt
Evan You 2 лет назад
Родитель
Сommit
0db336ff6c

+ 3 - 1
packages/runtime-core/__tests__/components/Suspense.spec.ts

@@ -1684,7 +1684,9 @@ describe('Suspense', () => {
     expect(serializeInner(root)).toBe('<div>async</div>')
     expect(serializeInner(root)).toBe('<div>async</div>')
 
 
     viewRef.value = 1
     viewRef.value = 1
-    await nextTick() //TypeError: Cannot read properties of null (reading 'parentNode'),This has been fixed
+    await nextTick()
+    // TypeError: Cannot read properties of null (reading 'parentNode')
+    // This has been fixed
     expect(serializeInner(root)).toBe(`<div>sync</div>`)
     expect(serializeInner(root)).toBe(`<div>sync</div>`)
   })
   })
 
 

+ 11 - 3
packages/runtime-core/src/componentRenderUtils.ts

@@ -428,8 +428,16 @@ export function updateHOCHostEl(
   { vnode, parent }: ComponentInternalInstance,
   { vnode, parent }: ComponentInternalInstance,
   el: typeof vnode.el // HostNode
   el: typeof vnode.el // HostNode
 ) {
 ) {
-  while (parent && parent.subTree === vnode) {
-    ;(vnode = parent.vnode).el = el
-    parent = parent.parent
+  while (parent) {
+    const root = parent.subTree
+    if (root.suspense && root.suspense.activeBranch === vnode) {
+      root.el = vnode.el
+    }
+    if (root === vnode) {
+      ;(vnode = parent.vnode).el = el
+      parent = parent.parent
+    } else {
+      break
+    }
   }
   }
 }
 }

+ 0 - 4
packages/runtime-core/src/renderer.ts

@@ -1241,10 +1241,6 @@ function baseCreateRenderer(
       if (!initialVNode.el) {
       if (!initialVNode.el) {
         const placeholder = (instance.subTree = createVNode(Comment))
         const placeholder = (instance.subTree = createVNode(Comment))
         processCommentNode(null, placeholder, container!, anchor)
         processCommentNode(null, placeholder, container!, anchor)
-        // This noramlly gets setup by the following `setupRenderEffect`.
-        // But the call is skipped in initial mounting of async element.
-        // Thus, manually patching is required here or it will result in a crash during parent component update.
-        initialVNode.el = placeholder.el
       }
       }
       return
       return
     }
     }