diff --git a/src/core/instance/init.js b/src/core/instance/init.js index 9d36c83ae3f..ddf808e4116 100644 --- a/src/core/instance/init.js +++ b/src/core/instance/init.js @@ -115,24 +115,27 @@ export function resolveConstructorOptions (Ctor: Class) { function resolveModifiedOptions (Ctor: Class): ?Object { let modified const latest = Ctor.options + const extended = Ctor.extendOptions const sealed = Ctor.sealedOptions for (const key in latest) { if (latest[key] !== sealed[key]) { if (!modified) modified = {} - modified[key] = dedupe(latest[key], sealed[key]) + modified[key] = dedupe(latest[key], extended[key], sealed[key]) } } return modified } -function dedupe (latest, sealed) { +function dedupe (latest, extended, sealed) { // compare latest and sealed to ensure lifecycle hooks won't be duplicated // between merges if (Array.isArray(latest)) { const res = [] sealed = Array.isArray(sealed) ? sealed : [sealed] + extended = Array.isArray(extended) ? extended : [extended] for (let i = 0; i < latest.length; i++) { - if (sealed.indexOf(latest[i]) < 0) { + // push original options and not sealed options to exclude duplicated options + if (extended.indexOf(latest[i]) >= 0 || sealed.indexOf(latest[i]) < 0) { res.push(latest[i]) } } diff --git a/test/unit/features/global-api/mixin.spec.js b/test/unit/features/global-api/mixin.spec.js index f452dbed8d2..bcf962402c2 100644 --- a/test/unit/features/global-api/mixin.spec.js +++ b/test/unit/features/global-api/mixin.spec.js @@ -141,4 +141,25 @@ describe('Global API: mixin', () => { }) expect(spy).toHaveBeenCalledWith('hello') }) + + // vue-class-component#87 + it('should not drop original lifecycle hooks', () => { + const base = jasmine.createSpy('base') + + const Base = Vue.extend({ + beforeCreate: base + }) + + const injected = jasmine.createSpy('injected') + + // inject a function + Base.options.beforeCreate = Base.options.beforeCreate.concat(injected) + + Vue.mixin({}) + + new Base({}) + + expect(base).toHaveBeenCalled() + expect(injected).toHaveBeenCalled() + }) })