Skip to content

Commit 0d16efe

Browse files
committed
wip: new merge function
1 parent 4e9545e commit 0d16efe

File tree

4 files changed

+125
-29
lines changed

4 files changed

+125
-29
lines changed

src/mount.ts

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -160,34 +160,34 @@ export function mount(
160160
}
161161

162162
// AppConfig
163-
if (global?.config) {
163+
if (global.config) {
164164
for (const [k, v] of Object.entries(global.config)) {
165165
app.config[k] = v
166166
}
167167
}
168168

169169
// use and plugins from mounting options
170-
if (global?.plugins) {
170+
if (global.plugins) {
171171
for (const use of global.plugins) app.use(use)
172172
}
173173

174174
// use any mixins from mounting options
175-
if (global?.mixins) {
175+
if (global.mixins) {
176176
for (const mixin of global.mixins) app.mixin(mixin)
177177
}
178178

179-
if (global?.components) {
179+
if (global.components) {
180180
for (const key of Object.keys(global.components))
181181
app.component(key, global.components[key])
182182
}
183183

184-
if (global?.directives) {
184+
if (global.directives) {
185185
for (const key of Object.keys(global.directives))
186186
app.directive(key, global.directives[key])
187187
}
188188

189189
// provide any values passed via provides mounting option
190-
if (global?.provide) {
190+
if (global.provide) {
191191
for (const key of Reflect.ownKeys(global.provide)) {
192192
// @ts-ignore: https://github.com/microsoft/TypeScript/issues/1863
193193
app.provide(key, global.provide[key])
@@ -198,8 +198,8 @@ export function mount(
198198
app.mixin(attachEmitListener())
199199

200200
// stubs
201-
if (options?.global?.stubs || options?.shallow) {
202-
stubComponents(options?.global?.stubs, options?.shallow)
201+
if (global.stubs || options?.shallow) {
202+
stubComponents(global.stubs, options?.shallow)
203203
} else {
204204
transformVNodeArgs()
205205
}

src/utils.ts

Lines changed: 23 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -2,29 +2,33 @@ import { GlobalMountOptions } from './types'
22

33
const isString = (val: unknown): val is string => typeof val === 'string'
44

5-
// Deep merge function, adapted from from https://gist.github.com/ahtcx/0cd94e62691f539160b32ecda18af3d6
6-
// Merge a `source` object to a `target` recursively
7-
const merge = (target: object, source: object) => {
8-
// Iterate through `source` properties and if an `Object` set property to merge of `target` and `source` properties
9-
for (const key of Object.keys(source)) {
10-
if (!target[key]) {
11-
target[key] = source[key]
12-
} else {
13-
if (source[key] instanceof Object) {
14-
Object.assign(source[key], merge(target[key], source[key]))
15-
}
16-
}
17-
}
18-
19-
Object.assign(target || {}, source)
20-
}
21-
225
function mergeGlobalProperties(
236
configGlobal: GlobalMountOptions = {},
247
mountGlobal: GlobalMountOptions = {}
258
): GlobalMountOptions {
26-
merge(configGlobal, mountGlobal)
27-
return configGlobal
9+
const {
10+
mixins: configMixins = [],
11+
plugins: configPlugins = [],
12+
...configRest
13+
} = configGlobal
14+
const {
15+
mixins: mountMixins = [],
16+
plugins: mountPlugins = [],
17+
...mountRest
18+
} = mountGlobal
19+
const mixins = [...configMixins, ...mountMixins]
20+
const plugins = [...configPlugins, ...mountPlugins]
21+
22+
return {
23+
mixins,
24+
plugins,
25+
components: { ...configRest.components, ...mountRest.components },
26+
provide: { ...configRest.provide, ...mountRest.provide },
27+
mocks: { ...configRest.mocks, ...mountRest.mocks },
28+
config: { ...configRest.config, ...mountRest.config },
29+
directives: { ...configRest.directives, ...mountRest.directives },
30+
stubs: { ...configRest.stubs, ...mountRest.stubs }
31+
}
2832
}
2933

3034
export { isString, mergeGlobalProperties }

tests/config.spec.ts

Lines changed: 93 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { h } from 'vue'
1+
import { h, inject } from 'vue'
22
import { config, mount } from '../src'
33
import Hello from './components/Hello.vue'
44

@@ -108,6 +108,44 @@ describe('config', () => {
108108
})
109109
})
110110

111+
describe('provide', () => {
112+
it('sets a provide everywhere', () => {
113+
config.global.provide = {
114+
theme: 'dark'
115+
}
116+
const Comp = {
117+
setup() {
118+
const theme = inject('theme')
119+
return () => h('div', theme)
120+
}
121+
}
122+
123+
const wrapper = mount(Comp)
124+
expect(wrapper.html()).toContain('dark')
125+
})
126+
127+
it('overrides with a local provide', () => {
128+
config.global.provide = {
129+
theme: 'dark'
130+
}
131+
const Comp = {
132+
setup() {
133+
const theme = inject('theme')
134+
return () => h('div', theme)
135+
}
136+
}
137+
138+
const wrapper = mount(Comp, {
139+
global: {
140+
provide: {
141+
theme: 'light'
142+
}
143+
}
144+
})
145+
expect(wrapper.html()).toContain('light')
146+
})
147+
})
148+
111149
describe('mixins', () => {
112150
const createdHook = jest.fn()
113151
const mixin = {
@@ -149,4 +187,58 @@ describe('config', () => {
149187
expect(createdHook).toHaveBeenCalledTimes(2)
150188
})
151189
})
190+
191+
describe('stubs', () => {
192+
const Foo = {
193+
name: 'Foo',
194+
render() {
195+
return h('div', 'real foo')
196+
}
197+
}
198+
199+
const Component = {
200+
render() {
201+
return h('div', h(Foo))
202+
}
203+
}
204+
205+
it('sets a stub globally', () => {
206+
config.global.stubs = {
207+
Foo: {
208+
render() {
209+
return h('div', 'foo stub')
210+
}
211+
}
212+
}
213+
214+
const wrapper = mount(Component)
215+
216+
// once on root, once in the mounted component
217+
expect(wrapper.html()).toContain('foo stub')
218+
})
219+
220+
xit('overrides config stub with locally defined stub', () => {
221+
config.global.stubs = {
222+
Foo: {
223+
render() {
224+
return h('div', 'config foo stub')
225+
}
226+
}
227+
}
228+
229+
const wrapper = mount(Component, {
230+
global: {
231+
stubs: {
232+
Foo: {
233+
render() {
234+
return h('div', 'local foo stub')
235+
}
236+
}
237+
}
238+
}
239+
})
240+
241+
expect(wrapper.html()).toContain('local foo stub')
242+
})
243+
})
152244
})

tests/shallowMount.spec.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -26,7 +26,7 @@ describe('shallowMount', () => {
2626
)
2727
})
2828

29-
it('stubs all components, but allows providing custom stub', () => {
29+
it.only('stubs all components, but allows providing custom stub', () => {
3030
const wrapper = mount(ComponentWithChildren, {
3131
shallow: true,
3232
global: {

0 commit comments

Comments
 (0)