Skip to content

Commit 5d75a17

Browse files
fix(Suspence): handle Suspense + KeepAlive HMR updating edge case (#13076)
close #13075
1 parent 55922ff commit 5d75a17

File tree

3 files changed

+56
-4
lines changed

3 files changed

+56
-4
lines changed

packages/runtime-core/__tests__/hmr.spec.ts

Lines changed: 52 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -895,6 +895,58 @@ describe('hot module replacement', () => {
895895
expect(serializeInner(root)).toBe('<div>bar</div>')
896896
})
897897

898+
test('multi reload child wrapped in Suspense + KeepAlive', async () => {
899+
const id = 'test-child-reload-3'
900+
const Child: ComponentOptions = {
901+
__hmrId: id,
902+
setup() {
903+
const count = ref(0)
904+
return { count }
905+
},
906+
render: compileToFunction(`<div>{{ count }}</div>`),
907+
}
908+
createRecord(id, Child)
909+
910+
const appId = 'test-app-id'
911+
const App: ComponentOptions = {
912+
__hmrId: appId,
913+
components: { Child },
914+
render: compileToFunction(`
915+
<KeepAlive>
916+
<Suspense>
917+
<Child />
918+
</Suspense>
919+
</KeepAlive>
920+
`),
921+
}
922+
923+
const root = nodeOps.createElement('div')
924+
render(h(App), root)
925+
expect(serializeInner(root)).toBe('<div>0</div>')
926+
await timeout()
927+
reload(id, {
928+
__hmrId: id,
929+
setup() {
930+
const count = ref(1)
931+
return { count }
932+
},
933+
render: compileToFunction(`<div>{{ count }}</div>`),
934+
})
935+
await timeout()
936+
expect(serializeInner(root)).toBe('<div>1</div>')
937+
938+
reload(id, {
939+
__hmrId: id,
940+
setup() {
941+
const count = ref(2)
942+
return { count }
943+
},
944+
render: compileToFunction(`<div>{{ count }}</div>`),
945+
})
946+
await timeout()
947+
expect(serializeInner(root)).toBe('<div>2</div>')
948+
})
949+
898950
test('rerender for nested component', () => {
899951
const id = 'child-nested-rerender'
900952
const Foo: ComponentOptions = {

packages/runtime-core/src/components/BaseTransition.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -204,7 +204,7 @@ const BaseTransitionImpl: ComponentOptions = {
204204
if (
205205
oldInnerChild &&
206206
oldInnerChild.type !== Comment &&
207-
!isSameVNodeType(innerChild, oldInnerChild) &&
207+
!isSameVNodeType(oldInnerChild, innerChild) &&
208208
recursiveGetSubtree(instance).type !== Comment
209209
) {
210210
let leavingHooks = resolveTransitionHooks(

packages/runtime-core/src/components/Suspense.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -235,7 +235,7 @@ function patchSuspense(
235235
const { activeBranch, pendingBranch, isInFallback, isHydrating } = suspense
236236
if (pendingBranch) {
237237
suspense.pendingBranch = newBranch
238-
if (isSameVNodeType(newBranch, pendingBranch)) {
238+
if (isSameVNodeType(pendingBranch, newBranch)) {
239239
// same root type but content may have changed.
240240
patch(
241241
pendingBranch,
@@ -321,7 +321,7 @@ function patchSuspense(
321321
)
322322
setActiveBranch(suspense, newFallback)
323323
}
324-
} else if (activeBranch && isSameVNodeType(newBranch, activeBranch)) {
324+
} else if (activeBranch && isSameVNodeType(activeBranch, newBranch)) {
325325
// toggled "back" to current active branch
326326
patch(
327327
activeBranch,
@@ -355,7 +355,7 @@ function patchSuspense(
355355
}
356356
}
357357
} else {
358-
if (activeBranch && isSameVNodeType(newBranch, activeBranch)) {
358+
if (activeBranch && isSameVNodeType(activeBranch, newBranch)) {
359359
// root did not change, just normal patch
360360
patch(
361361
activeBranch,

0 commit comments

Comments
 (0)