Skip to content

Commit

Permalink
fix(runtime-core): ensure that errors in slot function execution do n…
Browse files Browse the repository at this point in the history
…ot affect block tracking (#5670)

fix #5657
  • Loading branch information
javastation committed Oct 14, 2022
1 parent 5ee4053 commit 82a73da
Show file tree
Hide file tree
Showing 2 changed files with 34 additions and 6 deletions.
28 changes: 26 additions & 2 deletions packages/runtime-core/__tests__/vnode.spec.ts
Expand Up @@ -8,11 +8,12 @@ import {
cloneVNode,
mergeProps,
normalizeVNode,
transformVNodeArgs
transformVNodeArgs,
isBlockTreeEnabled
} from '../src/vnode'
import { Data } from '../src/component'
import { ShapeFlags, PatchFlags } from '@vue/shared'
import { h, reactive, isReactive, setBlockTracking, ref } from '../src'
import { h, reactive, isReactive, setBlockTracking, ref, withCtx } from '../src'
import { createApp, nodeOps, serializeInner } from '@vue/runtime-test'
import { setCurrentRenderingInstance } from '../src/componentRenderContext'

Expand Down Expand Up @@ -614,6 +615,29 @@ describe('vnode', () => {
]))
expect(vnode.dynamicChildren).toStrictEqual([])
})
// #5657
test('error of slot function execution should not affect block tracking', () => {
expect(isBlockTreeEnabled).toStrictEqual(1)
const slotFn = withCtx(
() => {
throw new Error('slot execution error')
},
{ type: {}, appContext: {} } as any
)
const Parent = {
setup(_: any, { slots }: any) {
return () => {
try {
slots.default()
} catch (e) {}
}
}
}
const vnode =
(openBlock(), createBlock(Parent, null, { default: slotFn }))
createApp(vnode).mount(nodeOps.createElement('div'))
expect(isBlockTreeEnabled).toStrictEqual(1)
})
})

describe('transformVNodeArgs', () => {
Expand Down
12 changes: 8 additions & 4 deletions packages/runtime-core/src/componentRenderContext.ts
Expand Up @@ -89,10 +89,14 @@ export function withCtx(
setBlockTracking(-1)
}
const prevInstance = setCurrentRenderingInstance(ctx)
const res = fn(...args)
setCurrentRenderingInstance(prevInstance)
if (renderFnWithContext._d) {
setBlockTracking(1)
let res
try {
res = fn(...args)
} finally {
setCurrentRenderingInstance(prevInstance)
if (renderFnWithContext._d) {
setBlockTracking(1)
}
}

if (__DEV__ || __FEATURE_PROD_DEVTOOLS__) {
Expand Down

0 comments on commit 82a73da

Please sign in to comment.