Skip to content

Commit 4a8f975

Browse files
pimlieTheAlexLichter
authored andcommitted
fix: afterNavigation logic (its never set in options)
1 parent 419951c commit 4a8f975

File tree

4 files changed

+40
-56
lines changed

4 files changed

+40
-56
lines changed

src/shared/mixin.js

Lines changed: 14 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,8 @@
11
import triggerUpdate from '../client/triggerUpdate'
2-
import hasMetaInfo from './hasMetaInfo'
2+
import { hasMetaInfo } from './meta-helpers'
33
import { isUndefined, isFunction } from './is-type'
44
import { ensuredPush } from './ensure'
5+
import { addNavGuards } from './nav-guards'
56

67
export default function createMixin(Vue, options) {
78
// for which Vue lifecycle hooks should the metaInfo be refreshed
@@ -14,7 +15,7 @@ export default function createMixin(Vue, options) {
1415
get() {
1516
// Show deprecation warning once when devtools enabled
1617
if (Vue.config.devtools && !this.$root._vueMeta.hasMetaInfoDeprecationWarningShown) {
17-
console.warn('VueMeta DeprecationWarning: _hasMetaInfo has been deprecated and will be removed in a future version. Please import hasMetaInfo and use hasMetaInfo(vm) instead') // eslint-disable-line no-console
18+
console.warn('VueMeta DeprecationWarning: _hasMetaInfo has been deprecated and will be removed in a future version. Please use hasMetaInfo(vm) instead') // eslint-disable-line no-console
1819
this.$root._vueMeta.hasMetaInfoDeprecationWarningShown = true
1920
}
2021
return hasMetaInfo(this)
@@ -71,39 +72,32 @@ export default function createMixin(Vue, options) {
7172
this.$root._vueMeta.initialized = this.$isServer
7273

7374
if (!this.$root._vueMeta.initialized) {
74-
const $rootMeta = this.$root.$meta()
75-
7675
ensuredPush(this.$options, 'mounted', () => {
7776
if (!this.$root._vueMeta.initialized) {
7877
// refresh meta in nextTick so all child components have loaded
7978
this.$nextTick(function () {
80-
$rootMeta.refresh()
79+
this.$root.$meta().refresh()
8180
this.$root._vueMeta.initialized = true
8281
})
8382
}
8483
})
8584

86-
// add vue-router navigation guard to prevent multiple updates during navigation
87-
// only usefull on the client side
88-
if (options.refreshOnceOnNavigation && this.$root.$router) {
89-
const $router = this.$root.$router
90-
$router.beforeEach((to, from, next) => {
91-
$rootMeta.pause()
92-
next()
93-
})
94-
95-
$router.afterEach(() => {
96-
const { vm, metaInfo } = $rootMeta.resume()
97-
if (metaInfo && metaInfo.afterNavigation && isFunction(metaInfo.afterNavigation)) {
98-
metaInfo.afterNavigation.call(vm, metaInfo)
99-
}
100-
})
85+
// add the navigation guards if they havent been added yet
86+
if (options.refreshOnceOnNavigation) {
87+
addNavGuards(this)
10188
}
10289
}
10390
}
10491

10592
// do not trigger refresh on the server side
10693
if (!this.$isServer) {
94+
// add the navigation guards if they havent been added yet
95+
// if metaInfo is defined as a function, this does call the computed fn redundantly
96+
// but as Vue internally caches the results of computed props it shouldnt hurt performance
97+
if (this.$options[options.keyName].afterNavigation) {
98+
addNavGuards(this)
99+
}
100+
107101
// no need to add this hooks on server side
108102
updateOnLifecycleHook.forEach((lifecycleHook) => {
109103
ensuredPush(this.$options, lifecycleHook, () => triggerUpdate(this, lifecycleHook))

src/shared/nav-guards.js

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
import { isFunction } from './is-type'
2+
3+
export function addNavGuards(vm) {
4+
// return when nav guards already added or no router exists
5+
if (vm.$root._vueMeta.navGuards || !vm.$root.$router) {
6+
return
7+
}
8+
9+
vm.$root._vueMeta.navGuards = true
10+
11+
const $router = vm.$root.$router
12+
const $meta = vm.$root.$meta()
13+
14+
$router.beforeEach((to, from, next) => {
15+
$meta.pause()
16+
next()
17+
})
18+
19+
$router.afterEach(() => {
20+
const { metaInfo } = $meta.resume()
21+
if (metaInfo && metaInfo.afterNavigation && isFunction(metaInfo.afterNavigation)) {
22+
metaInfo.afterNavigation(metaInfo)
23+
}
24+
})
25+
}

src/shared/options.js

Lines changed: 1 addition & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
import { isObject, isFunction } from './is-type'
1+
import { isObject } from './is-type'
22
import { defaultOptions } from './constants'
33

44
export default function setOptions(options) {
@@ -11,15 +11,5 @@ export default function setOptions(options) {
1111
}
1212
}
1313

14-
if (options.afterNavigation && !isFunction(options.afterNavigation)) {
15-
console.warn(`afterNavigation should be a function, received ${typeof options.afterNavigation} instead`) // eslint-disable-line no-console
16-
options.afterNavigation = void 0
17-
return options
18-
}
19-
20-
if (options.afterNavigation && !options.refreshOnceOnNavigation) {
21-
options.refreshOnceOnNavigation = true
22-
}
23-
2414
return options
2515
}

test/unit/shared.test.js

Lines changed: 0 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -6,8 +6,6 @@ import setOptions from '../../src/shared/options'
66
import { hasGlobalWindowFn } from '../../src/shared/window'
77
import { defaultOptions } from '../../src/shared/constants'
88

9-
const noop = () => {}
10-
119
describe('shared', () => {
1210
test('ensureIsArray ensures var is array', () => {
1311
let a = { p: 1 }
@@ -38,27 +36,4 @@ describe('shared', () => {
3836
expect(options.contentKeyName).toBeDefined()
3937
expect(options.contentKeyName).toBe(defaultOptions.contentKeyName)
4038
})
41-
42-
test('setOptions warns when afterNavigation not fn', () => {
43-
const warn = jest.spyOn(console, 'warn').mockImplementation(noop)
44-
45-
let options = { afterNavigation: true }
46-
options = setOptions(options)
47-
48-
expect(warn).toHaveBeenCalledTimes(1)
49-
expect(options.afterNavigation).toBeUndefined()
50-
51-
warn.mockRestore()
52-
})
53-
test('setOptions sets refreshOnceOnNavigation when afterNavigation defined', () => {
54-
const warn = jest.spyOn(console, 'warn').mockImplementation(noop)
55-
56-
let options = { afterNavigation: noop }
57-
options = setOptions(options)
58-
59-
expect(warn).not.toHaveBeenCalled()
60-
expect(options.refreshOnceOnNavigation).toBe(true)
61-
62-
warn.mockRestore()
63-
})
6439
})

0 commit comments

Comments
 (0)