@@ -508,4 +508,126 @@ describe('e2e: TransitionGroup', () => {
508508
509509 expect ( `<TransitionGroup> children must be keyed` ) . toHaveBeenWarned ( )
510510 } )
511+
512+ // #5168, #7898, #9067
513+ test (
514+ 'avoid set transition hooks for comment node' ,
515+ async ( ) => {
516+ await page ( ) . evaluate ( duration => {
517+ const { createApp, ref, h, createCommentVNode } = ( window as any ) . Vue
518+
519+ const show = ref ( false )
520+ createApp ( {
521+ template : `
522+ <div id="container">
523+ <transition-group name="test">
524+ <div v-for="item in items" :key="item" class="test">{{item}}</div>
525+ <Child key="child"/>
526+ </transition-group>
527+ </div>
528+ <button id="toggleBtn" @click="click">button</button>
529+ ` ,
530+ components : {
531+ Child : {
532+ setup ( ) {
533+ return ( ) =>
534+ show . value
535+ ? h ( 'div' , { class : 'test' } , 'child' )
536+ : createCommentVNode ( 'v-if' , true )
537+ } ,
538+ } ,
539+ } ,
540+ setup : ( ) => {
541+ const items = ref ( [ ] )
542+ const click = ( ) => {
543+ items . value = [ 'a' , 'b' , 'c' ]
544+ setTimeout ( ( ) => {
545+ show . value = true
546+ } , duration )
547+ }
548+ return { click, items }
549+ } ,
550+ } ) . mount ( '#app' )
551+ } , duration )
552+
553+ expect ( await html ( '#container' ) ) . toBe ( `<!--v-if-->` )
554+
555+ expect ( await htmlWhenTransitionStart ( ) ) . toBe (
556+ `<div class="test test-enter-from test-enter-active">a</div>` +
557+ `<div class="test test-enter-from test-enter-active">b</div>` +
558+ `<div class="test test-enter-from test-enter-active">c</div>` +
559+ `<!--v-if-->` ,
560+ )
561+
562+ await transitionFinish ( duration )
563+ await nextFrame ( )
564+ expect ( await html ( '#container' ) ) . toBe (
565+ `<div class="test">a</div>` +
566+ `<div class="test">b</div>` +
567+ `<div class="test">c</div>` +
568+ `<div class="test test-enter-active test-enter-to">child</div>` ,
569+ )
570+
571+ await transitionFinish ( duration )
572+ expect ( await html ( '#container' ) ) . toBe (
573+ `<div class="test">a</div>` +
574+ `<div class="test">b</div>` +
575+ `<div class="test">c</div>` +
576+ `<div class="test">child</div>` ,
577+ )
578+ } ,
579+ E2E_TIMEOUT ,
580+ )
581+
582+ // #4621, #4622, #5153
583+ test (
584+ 'avoid set transition hooks for text node' ,
585+ async ( ) => {
586+ await page ( ) . evaluate ( ( ) => {
587+ const { createApp, ref } = ( window as any ) . Vue
588+ const app = createApp ( {
589+ template : `
590+ <div id="container">
591+ <transition-group name="test">
592+ <div class="test">foo</div>
593+ <div class="test" v-if="show">bar</div>
594+ </transition-group>
595+ </div>
596+ <button id="toggleBtn" @click="click">button</button>
597+ ` ,
598+ setup : ( ) => {
599+ const show = ref ( false )
600+ const click = ( ) => {
601+ show . value = true
602+ }
603+ return { show, click }
604+ } ,
605+ } )
606+
607+ app . config . compilerOptions . whitespace = 'preserve'
608+ app . mount ( '#app' )
609+ } )
610+
611+ expect ( await html ( '#container' ) ) . toBe ( `<div class="test">foo</div>` + ` ` )
612+
613+ expect ( await htmlWhenTransitionStart ( ) ) . toBe (
614+ `<div class="test">foo</div>` +
615+ ` ` +
616+ `<div class="test test-enter-from test-enter-active">bar</div>` ,
617+ )
618+
619+ await nextFrame ( )
620+ expect ( await html ( '#container' ) ) . toBe (
621+ `<div class="test">foo</div>` +
622+ ` ` +
623+ `<div class="test test-enter-active test-enter-to">bar</div>` ,
624+ )
625+
626+ await transitionFinish ( duration )
627+ expect ( await html ( '#container' ) ) . toBe (
628+ `<div class="test">foo</div>` + ` ` + `<div class="test">bar</div>` ,
629+ )
630+ } ,
631+ E2E_TIMEOUT ,
632+ )
511633} )
0 commit comments