@@ -4,59 +4,58 @@ import { createSlotVNodes } from './create-slot-vnodes'
44import addMocks from './add-mocks'
55import { addEventLogger } from './log-events'
66import { addStubs } from './add-stubs'
7- import { throwError } from 'shared/util'
8- import { VUE_VERSION } from 'shared/consts'
9- import {
10- compileTemplate ,
11- compileTemplateForSlots
12- } from 'shared/compile-template'
7+ import { compileTemplate } from 'shared/compile-template'
138import extractInstanceOptions from './extract-instance-options'
14- import createFunctionalComponent from './create-functional-component'
15- import { componentNeedsCompiling , isPlainObject } from 'shared/validators'
16- import { validateSlots } from './validate-slots'
9+ import {
10+ componentNeedsCompiling ,
11+ isConstructor
12+ } from 'shared/validators'
1713import createScopedSlots from './create-scoped-slots'
1814import { createStubsFromStubsObject } from './create-component-stubs'
1915import { patchCreateElement } from './patch-create-element'
20- import { isConstructor } from 'shared/validators'
2116
22- function vueExtendUnsupportedOption ( option : string ) {
23- return `options.${ option } is not supported for ` +
24- `components created with Vue.extend in Vue < 2.3. ` +
25- `You can set ${ option } to false to mount the component.`
17+ function createContext ( options , scopedSlots ) {
18+ const on = {
19+ ...( options . context && options . context . on ) ,
20+ ...options . listeners
21+ }
22+ return {
23+ attrs : {
24+ ...options . attrs ,
25+ // pass as attrs so that inheritAttrs works correctly
26+ // propsData should take precedence over attrs
27+ ...options . propsData
28+ } ,
29+ ...( options . context || { } ) ,
30+ on,
31+ scopedSlots
32+ }
2633}
2734
28- // these options aren't supported if Vue is version < 2.3
29- // for components using Vue.extend. This is due to a bug
30- // that means the mixins we use to add properties are not applied
31- // correctly
32- const UNSUPPORTED_VERSION_OPTIONS = [
33- 'mocks' ,
34- 'stubs' ,
35- 'localVue'
36- ]
35+ function createChildren ( vm , h , { slots, context } ) {
36+ const slotVNodes = slots
37+ ? createSlotVNodes ( vm , slots )
38+ : undefined
39+ return (
40+ context &&
41+ context . children &&
42+ context . children . map ( x => ( typeof x === 'function' ? x ( h ) : x ) )
43+ ) || slotVNodes
44+ }
3745
3846export default function createInstance (
3947 component : Component ,
4048 options : Options ,
4149 _Vue : Component
4250) : Component {
43- if (
44- VUE_VERSION < 2.3 && isConstructor ( component )
45- ) {
46- UNSUPPORTED_VERSION_OPTIONS . forEach ( ( option ) => {
47- if ( options [ option ] ) {
48- throwError ( vueExtendUnsupportedOption ( option ) )
49- }
50- } )
51- }
52-
53- let componentOptions = isConstructor ( component )
51+ const componentOptions = isConstructor ( component )
5452 ? component . options
5553 : component
5654
5755 // instance options are options that are passed to the
5856 // root instance when it's instantiated
5957 const instanceOptions = extractInstanceOptions ( options )
58+
6059 const stubComponentsObject = createStubsFromStubsObject (
6160 componentOptions . components ,
6261 // $FlowIgnore
@@ -69,81 +68,30 @@ export default function createInstance (
6968 addStubs ( _Vue , stubComponentsObject )
7069 patchCreateElement ( _Vue , stubComponentsObject , options . shouldProxy )
7170
72- if ( componentOptions . functional ) {
73- componentOptions = createFunctionalComponent (
74- componentOptions ,
75- options ,
76- _Vue
77- )
78- } else if ( options . context ) {
79- throwError (
80- `mount.context can only be used when mounting a ` +
81- `functional component`
82- )
83- }
84-
8571 if ( componentNeedsCompiling ( componentOptions ) ) {
8672 compileTemplate ( componentOptions )
8773 }
8874
75+ // used to identify extended component using constructor
76+ componentOptions . $_vueTestUtils_original = component
77+
8978 // make sure all extends are based on this instance
9079 componentOptions . _base = _Vue
9180
9281 const Constructor = _Vue . extend ( componentOptions ) . extend ( instanceOptions )
9382
94- // used to identify extended component using constructor
95- Constructor . options . $_vueTestUtils_original = component
96-
97- if ( options . slots ) {
98- compileTemplateForSlots ( options . slots )
99- // validate slots outside of the createSlots function so
100- // that we can throw an error without it being caught by
101- // the Vue error handler
102- // $FlowIgnore
103- validateSlots ( options . slots )
104- }
105-
106- // Objects are not resolved in extended components in Vue < 2.5
107- // https://github.com/vuejs/vue/issues/6436
108- if (
109- options . provide &&
110- typeof options . provide === 'object' &&
111- VUE_VERSION < 2.5
112- ) {
113- const obj = { ...options . provide }
114- options . provide = ( ) => obj
115- }
116-
11783 const scopedSlots = createScopedSlots ( options . scopedSlots , _Vue )
11884
119- if ( options . parentComponent && ! isPlainObject ( options . parentComponent ) ) {
120- throwError (
121- `options.parentComponent should be a valid Vue component options object`
122- )
123- }
124-
12585 const parentComponentOptions = options . parentComponent || { }
86+
12687 parentComponentOptions . provide = options . provide
12788 parentComponentOptions . $_doNotStubChildren = true
128-
89+ parentComponentOptions . _isFunctionalContainer = componentOptions . functional
12990 parentComponentOptions . render = function ( h ) {
130- const slots = options . slots
131- ? createSlotVNodes ( this , options . slots )
132- : undefined
13391 return h (
13492 Constructor ,
135- {
136- ref : 'vm' ,
137- on : options . listeners ,
138- attrs : {
139- ...options . attrs ,
140- // pass as attrs so that inheritAttrs works correctly
141- // propsData should take precedence over attrs
142- ...options . propsData
143- } ,
144- scopedSlots
145- } ,
146- slots
93+ createContext ( options , scopedSlots ) ,
94+ createChildren ( this , h , options )
14795 )
14896 }
14997 const Parent = _Vue . extend ( parentComponentOptions )
0 commit comments