From: HcySunYang Date: Tue, 20 Oct 2020 18:59:55 +0000 (+0800) Subject: fix(runtime-core): non-stable Fragment should always unmount its children (#2445) X-Git-Tag: v3.0.2~2 X-Git-Url: http://git.ipfire.org/cgi-bin/gitweb.cgi?a=commitdiff_plain;h=fff62e2ee8accf31bb5ac5abdb4c0636216cfd0e;p=thirdparty%2Fvuejs%2Fcore.git fix(runtime-core): non-stable Fragment should always unmount its children (#2445) fix #2444 --- diff --git a/packages/runtime-core/__tests__/rendererOptimizedMode.spec.ts b/packages/runtime-core/__tests__/rendererOptimizedMode.spec.ts index 8b674b8a39..24f496caa7 100644 --- a/packages/runtime-core/__tests__/rendererOptimizedMode.spec.ts +++ b/packages/runtime-core/__tests__/rendererOptimizedMode.spec.ts @@ -475,4 +475,46 @@ describe('renderer: optimized mode', () => { render(null, root) expect(spy).toHaveBeenCalledTimes(1) }) + + // #2444 + // `KEYED_FRAGMENT` and `UNKEYED_FRAGMENT` always need to diff its children + test('non-stable Fragment always need to diff its children', () => { + const spyA = jest.fn() + const spyB = jest.fn() + const ChildA = { + setup() { + onBeforeUnmount(spyA) + return () => 'child' + } + } + const ChildB = { + setup() { + onBeforeUnmount(spyB) + return () => 'child' + } + } + const Parent = () => ( + openBlock(), + createBlock('div', null, [ + (openBlock(true), + createBlock( + Fragment, + null, + [createVNode(ChildA, { key: 0 })], + 128 /* KEYED_FRAGMENT */ + )), + (openBlock(true), + createBlock( + Fragment, + null, + [createVNode(ChildB)], + 256 /* UNKEYED_FRAGMENT */ + )) + ]) + ) + render(h(Parent), root) + render(null, root) + expect(spyA).toHaveBeenCalledTimes(1) + expect(spyB).toHaveBeenCalledTimes(1) + }) }) diff --git a/packages/runtime-core/src/renderer.ts b/packages/runtime-core/src/renderer.ts index db47c15ad5..f0182c16f6 100644 --- a/packages/runtime-core/src/renderer.ts +++ b/packages/runtime-core/src/renderer.ts @@ -2038,7 +2038,12 @@ function baseCreateRenderer( false, true ) - } else if (!optimized && shapeFlag & ShapeFlags.ARRAY_CHILDREN) { + } else if ( + (type === Fragment && + (patchFlag & PatchFlags.KEYED_FRAGMENT || + patchFlag & PatchFlags.UNKEYED_FRAGMENT)) || + (!optimized && shapeFlag & ShapeFlags.ARRAY_CHILDREN) + ) { unmountChildren(children as VNode[], parentComponent, parentSuspense) }