From 303655116f8ec78f3b0ac99569637ad868dfe246 Mon Sep 17 00:00:00 2001 From: Evan You Date: Thu, 20 Jul 2017 21:47:52 -0400 Subject: [PATCH] fix(provide/inject): merge provide properly from mixins close #6175 --- src/core/util/options.js | 2 +- test/unit/features/options/inject.spec.js | 41 +++++++++++++++++++++++ 2 files changed, 42 insertions(+), 1 deletion(-) diff --git a/src/core/util/options.js b/src/core/util/options.js index 465bb628..0d4f4eee 100644 --- a/src/core/util/options.js +++ b/src/core/util/options.js @@ -85,7 +85,7 @@ export function mergeDataOrFn ( return function mergedDataFn () { return mergeData( typeof childVal === 'function' ? childVal.call(this) : childVal, - parentVal.call(this) + typeof parentVal === 'function' ? parentVal.call(this) : parentVal ) } } else if (parentVal || childVal) { diff --git a/test/unit/features/options/inject.spec.js b/test/unit/features/options/inject.spec.js index d501cd02..e4d9f90e 100644 --- a/test/unit/features/options/inject.spec.js +++ b/test/unit/features/options/inject.spec.js @@ -382,6 +382,7 @@ describe('Options provide/inject', () => { expect(injected).toEqual(['foo', 'bar']) }) + it('should merge provide from mixins (functions)', () => { const mixinA = { provide: () => ({ foo: 'foo' }) } const mixinB = { provide: () => ({ bar: 'bar' }) } @@ -401,6 +402,7 @@ describe('Options provide/inject', () => { expect(injected).toEqual(['foo', 'bar']) }) + it('should merge provide from mixins (mix of objects and functions)', () => { const mixinA = { provide: { foo: 'foo' }} const mixinB = { provide: () => ({ bar: 'bar' }) } @@ -422,6 +424,7 @@ describe('Options provide/inject', () => { expect(injected).toEqual(['foo', 'bar', 'baz', 'bam']) }) + it('should merge provide from mixins and override existing keys', () => { const mixinA = { provide: { foo: 'foo' }} const mixinB = { provide: { foo: 'bar' }} @@ -441,6 +444,7 @@ describe('Options provide/inject', () => { expect(injected).toEqual(['bar']) }) + it('should merge provide when Vue.extend', () => { const mixinA = { provide: () => ({ foo: 'foo' }) } const child = { @@ -504,4 +508,41 @@ describe('Options provide/inject', () => { expect(isObserver(child.bar)).toBe(false) expect(isObserver(child.baz)).toBe(false) }) + + // #6175 + it('merge provide properly from mixins', () => { + const ProvideFooMixin = { + provide: { + foo: 'foo injected' + } + } + + const ProvideBarMixin = { + provide: { + bar: 'bar injected' + } + } + + const Child = { + inject: ['foo', 'bar'], + render (h) { + return h('div', [`foo: ${this.foo}, `, `bar: ${this.bar}`]) + } + } + + const Parent = { + mixins: [ProvideFooMixin, ProvideBarMixin], + render (h) { + return h(Child) + } + } + + const vm = new Vue({ + render (h) { + return h(Parent) + } + }).$mount() + + expect(vm.$el.textContent).toBe(`foo: foo injected, bar: bar injected`) + }) })