File tree Expand file tree Collapse file tree 3 files changed +57
-1
lines changed Expand file tree Collapse file tree 3 files changed +57
-1
lines changed Original file line number Diff line number Diff line change 4
4
getCurrentInstance ,
5
5
} from '../component'
6
6
import { resolveInjections } from '../componentOptions'
7
+ import type { ContextualRenderFn } from '../componentRenderContext'
7
8
import type { InternalSlots } from '../componentSlots'
8
9
import { getCompatListeners } from './instanceListeners'
9
10
import { compatH } from './renderFn'
@@ -15,7 +16,10 @@ const normalizedFunctionalComponentMap = new WeakMap<
15
16
export const legacySlotProxyHandlers : ProxyHandler < InternalSlots > = {
16
17
get ( target , key : string ) {
17
18
const slot = target [ key ]
18
- return slot && slot ( )
19
+ return (
20
+ slot &&
21
+ ( ( slot as ContextualRenderFn ) . _ns /* non-scoped slot */ ? slot ( ) : slot )
22
+ )
19
23
} ,
20
24
}
21
25
Original file line number Diff line number Diff line change @@ -110,6 +110,12 @@ const normalizeSlot = (
110
110
} , ctx ) as Slot
111
111
// NOT a compiled slot
112
112
; ( normalized as ContextualRenderFn ) . _c = false
113
+ if ( __COMPAT__ ) {
114
+ // Preserve non-scoped slot flag (can be set in `convertLegacySlots`)
115
+ ; ( normalized as ContextualRenderFn ) . _ns = (
116
+ rawSlot as ContextualRenderFn
117
+ ) . _ns
118
+ }
113
119
return normalized
114
120
}
115
121
@@ -159,6 +165,9 @@ const normalizeVNodeSlots = (
159
165
}
160
166
const normalized = normalizeSlotValue ( children )
161
167
instance . slots . default = ( ) => normalized
168
+ if ( __COMPAT__ ) {
169
+ ; ( instance . slots . default as ContextualRenderFn ) . _ns = true
170
+ }
162
171
}
163
172
164
173
export const initSlots = (
Original file line number Diff line number Diff line change @@ -309,6 +309,49 @@ describe('INSTANCE_SCOPED_SLOTS', () => {
309
309
} )
310
310
} )
311
311
312
+ describe ( 'RENDER_FUNCTION' , ( ) => {
313
+ test ( 'should not auto invoke scoped slot accessed via $slots in a render function' , ( ) => {
314
+ new Vue ( {
315
+ template : `<child v-slot="{ msg }">{{ msg }}</child>` ,
316
+ components : {
317
+ child : {
318
+ compatConfig : { MODE : 2 } ,
319
+ render ( ) {
320
+ expect ( ( ) => this . $slots . default ) . not . toThrow ( )
321
+ expect ( this . $slots . default ) . toBeTypeOf ( 'function' )
322
+ } ,
323
+ } ,
324
+ } ,
325
+ } ) . $mount ( )
326
+
327
+ expect (
328
+ deprecationData [ DeprecationTypes . RENDER_FUNCTION ] . message ,
329
+ ) . toHaveBeenWarned ( )
330
+ } )
331
+
332
+ test ( 'should auto invoke non-scoped slot accessed via $slots in a render function' , ( ) => {
333
+ const DEFAULT_SLOT_CONTENTS = 'foo'
334
+
335
+ new Vue ( {
336
+ template : `<child>${ DEFAULT_SLOT_CONTENTS } </child>` ,
337
+ components : {
338
+ child : {
339
+ compatConfig : { MODE : 2 } ,
340
+ render ( ) {
341
+ expect ( this . $slots . default [ 0 ] . children ) . toEqual (
342
+ DEFAULT_SLOT_CONTENTS ,
343
+ )
344
+ } ,
345
+ } ,
346
+ } ,
347
+ } ) . $mount ( )
348
+
349
+ expect (
350
+ deprecationData [ DeprecationTypes . RENDER_FUNCTION ] . message ,
351
+ ) . toHaveBeenWarned ( )
352
+ } )
353
+ } )
354
+
312
355
test ( 'INSTANCE_ATTR_CLASS_STYLE' , ( ) => {
313
356
const vm = new Vue ( {
314
357
template : `<child class="foo" style="color:red" id="ok" />` ,
You can’t perform that action at this time.
0 commit comments