@@ -826,12 +826,15 @@ function baseCreateRenderer(
826
826
const newProps = n2 . props || EMPTY_OBJ
827
827
let vnodeHook : VNodeHook | undefined | null
828
828
829
+ // disable recurse in beforeUpdate hooks
830
+ parentComponent && toggleRecurse ( parentComponent , false )
829
831
if ( ( vnodeHook = newProps . onVnodeBeforeUpdate ) ) {
830
832
invokeVNodeHook ( vnodeHook , parentComponent , n2 , n1 )
831
833
}
832
834
if ( dirs ) {
833
835
invokeDirectiveHook ( n2 , n1 , parentComponent , 'beforeUpdate' )
834
836
}
837
+ parentComponent && toggleRecurse ( parentComponent , true )
835
838
836
839
if ( __DEV__ && isHmrUpdating ) {
837
840
// HMR updated, force full diff
@@ -1318,7 +1321,7 @@ function baseCreateRenderer(
1318
1321
const { bm, m, parent } = instance
1319
1322
const isAsyncWrapperVNode = isAsyncWrapper ( initialVNode )
1320
1323
1321
- effect . allowRecurse = false
1324
+ toggleRecurse ( instance , false )
1322
1325
// beforeMount hook
1323
1326
if ( bm ) {
1324
1327
invokeArrayFns ( bm )
@@ -1336,7 +1339,7 @@ function baseCreateRenderer(
1336
1339
) {
1337
1340
instance . emit ( 'hook:beforeMount' )
1338
1341
}
1339
- effect . allowRecurse = true
1342
+ toggleRecurse ( instance , true )
1340
1343
1341
1344
if ( el && hydrateNode ) {
1342
1345
// vnode has adopted host node - perform hydration instead of mount.
@@ -1459,8 +1462,7 @@ function baseCreateRenderer(
1459
1462
}
1460
1463
1461
1464
// Disallow component effect recursion during pre-lifecycle hooks.
1462
- effect . allowRecurse = false
1463
-
1465
+ toggleRecurse ( instance , false )
1464
1466
if ( next ) {
1465
1467
next . el = vnode . el
1466
1468
updateComponentPreRender ( instance , next , optimized )
@@ -1482,8 +1484,7 @@ function baseCreateRenderer(
1482
1484
) {
1483
1485
instance . emit ( 'hook:beforeUpdate' )
1484
1486
}
1485
-
1486
- effect . allowRecurse = true
1487
+ toggleRecurse ( instance , true )
1487
1488
1488
1489
// render
1489
1490
if ( __DEV__ ) {
@@ -1552,17 +1553,17 @@ function baseCreateRenderer(
1552
1553
}
1553
1554
1554
1555
// create reactive effect for rendering
1555
- const effect = new ReactiveEffect (
1556
+ const effect = ( instance . effect = new ReactiveEffect (
1556
1557
componentUpdateFn ,
1557
1558
( ) => queueJob ( instance . update ) ,
1558
1559
instance . scope // track it in component's effect scope
1559
- )
1560
+ ) )
1560
1561
1561
1562
const update = ( instance . update = effect . run . bind ( effect ) as SchedulerJob )
1562
1563
update . id = instance . uid
1563
1564
// allowRecurse
1564
1565
// #1801, #2043 component render effects should allow recursive updates
1565
- effect . allowRecurse = update . allowRecurse = true
1566
+ toggleRecurse ( instance , true )
1566
1567
1567
1568
if ( __DEV__ ) {
1568
1569
effect . onTrack = instance . rtc
@@ -2455,6 +2456,13 @@ export function invokeVNodeHook(
2455
2456
] )
2456
2457
}
2457
2458
2459
+ function toggleRecurse (
2460
+ { effect, update } : ComponentInternalInstance ,
2461
+ allowed : boolean
2462
+ ) {
2463
+ effect . allowRecurse = update . allowRecurse = allowed
2464
+ }
2465
+
2458
2466
/**
2459
2467
* #1156
2460
2468
* When a component is HMR-enabled, we need to make sure that all static nodes
0 commit comments