From 8e82e54f8d647fbd765c4cf6526601393c42dd35 Mon Sep 17 00:00:00 2001 From: tonicli Date: Sat, 20 Apr 2024 09:42:43 +0800 Subject: [PATCH 1/3] fix(runtime-core): TypeError when using html comment in teleport close #10747 --- packages/runtime-core/src/renderer.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/runtime-core/src/renderer.ts b/packages/runtime-core/src/renderer.ts index c7dfbf45dd2..27f1b320a42 100644 --- a/packages/runtime-core/src/renderer.ts +++ b/packages/runtime-core/src/renderer.ts @@ -2471,7 +2471,7 @@ export function traverseStaticChildren(n1: VNode, n2: VNode, shallow = false) { } // also inherit for comment nodes, but not placeholders (e.g. v-if which // would have received .el during block patch) - if (__DEV__ && c2.type === Comment && !c2.el) { + if (c2.type === Comment && !c2.el) { c2.el = c1.el } } From 8a0b1fcd2a8e94ccd97607debf6f76de3ecc4c58 Mon Sep 17 00:00:00 2001 From: tonicli Date: Mon, 13 May 2024 18:11:19 +0800 Subject: [PATCH 2/3] test: add test case --- .../__tests__/components/Teleport.spec.ts | 73 ++++++++++++++++++- 1 file changed, 72 insertions(+), 1 deletion(-) diff --git a/packages/runtime-core/__tests__/components/Teleport.spec.ts b/packages/runtime-core/__tests__/components/Teleport.spec.ts index 9c85cd8beb6..588047f084e 100644 --- a/packages/runtime-core/__tests__/components/Teleport.spec.ts +++ b/packages/runtime-core/__tests__/components/Teleport.spec.ts @@ -13,11 +13,20 @@ import { nodeOps, ref, render, + serialize, serializeInner, withDirectives, } from '@vue/runtime-test' -import { Fragment, createVNode } from '../../src/vnode' +import { + Fragment, + createBlock, + createCommentVNode, + createTextVNode, + createVNode, + openBlock, +} from '../../src/vnode' import { compile, render as domRender } from 'vue' +import { toDisplayString } from '@vue/shared' describe('renderer: teleport', () => { test('should work', () => { @@ -129,6 +138,41 @@ describe('renderer: teleport', () => { expect(serializeInner(target)).toMatchInlineSnapshot(`"teleported"`) }) + test('should traverse comment node after updating in optimize mode', async () => { + const target = nodeOps.createElement('div') + const root = nodeOps.createElement('div') + const count = ref(0) + let teleport + + __DEV__ = false + render( + h(() => { + teleport = + (openBlock(), + createBlock(Teleport, { to: target }, [ + createCommentVNode('comment in teleport'), + ])) + return h('div', null, [ + createTextVNode(toDisplayString(count.value)), + teleport, + ]) + }), + root, + ) + const commentNode = teleport!.children[0].el + expect(serializeInner(root)).toMatchInlineSnapshot(`"
0
"`) + expect(serializeInner(target)).toMatchInlineSnapshot( + `""`, + ) + expect(serialize(commentNode)).toBe(``) + + count.value = 1 + await nextTick() + __DEV__ = true + expect(serializeInner(root)).toMatchInlineSnapshot(`"
1
"`) + expect(teleport!.children[0].el).toBe(commentNode) + }) + test('should remove children when unmounted', () => { const target = nodeOps.createElement('div') const root = nodeOps.createElement('div') @@ -151,6 +195,33 @@ describe('renderer: teleport', () => { testUnmount({ to: target, disabled: true }) testUnmount({ to: null, disabled: true }) }) + // #10747 + test('should unmount correctly when using top level comment in teleport', async () => { + const target = nodeOps.createElement('div') + const root = nodeOps.createElement('div') + const count = ref(0) + + __DEV__ = false + render( + h(() => { + return h('div', null, [ + createTextVNode(toDisplayString(count.value)), + (openBlock(), + createBlock(Teleport, { to: target }, [ + createCommentVNode('comment in teleport'), + ])), + ]) + }), + root, + ) + + count.value = 1 + + await nextTick() + __DEV__ = true + render(null, root) + expect(root.children.length).toBe(0) + }) test('component with multi roots should be removed when unmounted', () => { const target = nodeOps.createElement('div') From af25c8cc33ecfd44db4b439188dd012887261080 Mon Sep 17 00:00:00 2001 From: daiwei Date: Mon, 6 Jan 2025 21:21:37 +0800 Subject: [PATCH 3/3] chore: update test --- .../runtime-core/__tests__/components/Teleport.spec.ts | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/packages/runtime-core/__tests__/components/Teleport.spec.ts b/packages/runtime-core/__tests__/components/Teleport.spec.ts index fc0c2b3beb9..4739a17d534 100644 --- a/packages/runtime-core/__tests__/components/Teleport.spec.ts +++ b/packages/runtime-core/__tests__/components/Teleport.spec.ts @@ -274,16 +274,14 @@ describe('renderer: teleport', () => { root, ) const commentNode = teleport!.children[0].el - expect(serializeInner(root)).toMatchInlineSnapshot(`"
0
"`) - expect(serializeInner(target)).toMatchInlineSnapshot( - `""`, - ) + expect(serializeInner(root)).toBe(`
0
`) + expect(serializeInner(target)).toBe(``) expect(serialize(commentNode)).toBe(``) count.value = 1 await nextTick() __DEV__ = true - expect(serializeInner(root)).toMatchInlineSnapshot(`"
1
"`) + expect(serializeInner(root)).toBe(`
1
`) expect(teleport!.children[0].el).toBe(commentNode) })