用 NuxtLink 重新 运行 外部 JavaScript
Re-run external JavaScript with NuxtLink
我正在为我的 Nuxt 应用程序(Nuxt 通用模式、服务器端渲染 + 客户端导航)的客户端/前端设计使用多个外部 JavaScript-文件,将它们放在nuxt.config.js-文件.
nuxt.config.js
<script>
export default {
head () {
return {
script: [
{ src: '/scripts/jquery.min.js', body: true },
{ src: '/scripts/jquery.dropotron.min.js', body: true },
{ src: '/scripts/browser.min.js', body: true },
{ src: '/scripts/breakpoints.min.js', body: true },
{ src: '/scripts/util.js', body: true },
{ src: '/scripts/main.js', body: true },
{ src: '/scripts/owa.js', body: true }
]
}
}
}
</script>
初始页面浏览时一切正常,但不幸的是,当使用 NuxtLink 导航到另一个页面时,EventListeners 消失了。我由此得出结论,虚拟 DOM 已重新渲染,但一旦完成,JavaScript 函数不会再次 运行。
当然我可以使用 a-Tags 而不是 NuxtLink,这样整个站点将再次加载,脚本也会加载,但这是不好的做法,与 SPA 无关。
我已经尝试过 Nuxt 中间件,但是删除 Head 中的脚本(在示例代码中看到)不起作用。
middleware/rerunJs.js
const scripts = context.app.head.script
context.app.head.script = undefined
context.app.head.script = scripts
如有任何想法,我们将不胜感激!
更新
Client Console Output - Initial page load
Logging: rerunJs.js in middleware directory
Server based middleware
Print context.app.head.script:
[
{ src: '/scripts/jquery.min.js', body: true, defer: true },
{ src: '/scripts/jquery.dropotron.min.js', body: true, defer: true },
{ src: '/scripts/browser.min.js', body: true, defer: true },
{ src: '/scripts/breakpoints.min.js', body: true, defer: true },
{ src: '/scripts/util.js', body: true, defer: true },
{ src: '/scripts/main.js', body: true, defer: true },
{ src: '/scripts/owa.js', body: true }
]
Logging: index.vue in Nuxt pages directory
Logging: jquery.dropotron.min.js in static/scripts directory
Logging: main.js in static/scripts directory
Client Console Output - Navigating to Route '/' with NuxtLink
Logging: rerunJs.js in middleware directory
Client based middleware
Print context.app.head.script:
Array(7) [ {…}, {…}, {…}, {…}, {…}, {…}, {…} ]
解决方案
要重新运行外部JavaScript(即jQuery),当使用 NuxtLink 导航到另一个页面并且 Nuxt 设置为通用模式时,将使用两个生命周期挂钩。
首先,中间件应该从 head 中删除脚本。可以肯定的是,只有客户端会删除脚本。在初始页面加载时,中间件基于服务器和脚本 运行,即使不触发它们也是如此。
middleware/rerunJs.js
...
if (process.client) {
context.app.head.script = undefined
}
...
之后,所需页面的 mounted-Hook 应将脚本附加到正文的头部和末尾。
pages/index.vue
...
mounted () {
(function LoadMyJs () {
const docHeadObj = document.getElementsByTagName('head')[0]
const jqueryScript = document.createElement('script')
jqueryScript.outerHTML = '<scr' + 'ipt data-n-head="ssr" src="/scripts/jquery.min.js" data-body="true">' + ' </scr' + 'ipt>'
jqueryScript.src = '/scripts/jquery.min.js'
jqueryScript.defer = true
docHeadObj.appendChild(jqueryScript)
document.body.innerHTML = document.body.innerHTML + queryScript.outerHTML
}())
}
...
我正在为我的 Nuxt 应用程序(Nuxt 通用模式、服务器端渲染 + 客户端导航)的客户端/前端设计使用多个外部 JavaScript-文件,将它们放在nuxt.config.js-文件.
nuxt.config.js
<script>
export default {
head () {
return {
script: [
{ src: '/scripts/jquery.min.js', body: true },
{ src: '/scripts/jquery.dropotron.min.js', body: true },
{ src: '/scripts/browser.min.js', body: true },
{ src: '/scripts/breakpoints.min.js', body: true },
{ src: '/scripts/util.js', body: true },
{ src: '/scripts/main.js', body: true },
{ src: '/scripts/owa.js', body: true }
]
}
}
}
</script>
初始页面浏览时一切正常,但不幸的是,当使用 NuxtLink 导航到另一个页面时,EventListeners 消失了。我由此得出结论,虚拟 DOM 已重新渲染,但一旦完成,JavaScript 函数不会再次 运行。
当然我可以使用 a-Tags 而不是 NuxtLink,这样整个站点将再次加载,脚本也会加载,但这是不好的做法,与 SPA 无关。
我已经尝试过 Nuxt 中间件,但是删除 Head 中的脚本(在示例代码中看到)不起作用。
middleware/rerunJs.js
const scripts = context.app.head.script
context.app.head.script = undefined
context.app.head.script = scripts
如有任何想法,我们将不胜感激!
更新
Client Console Output - Initial page load
Logging: rerunJs.js in middleware directory
Server based middleware
Print context.app.head.script:
[
{ src: '/scripts/jquery.min.js', body: true, defer: true },
{ src: '/scripts/jquery.dropotron.min.js', body: true, defer: true },
{ src: '/scripts/browser.min.js', body: true, defer: true },
{ src: '/scripts/breakpoints.min.js', body: true, defer: true },
{ src: '/scripts/util.js', body: true, defer: true },
{ src: '/scripts/main.js', body: true, defer: true },
{ src: '/scripts/owa.js', body: true }
]
Logging: index.vue in Nuxt pages directory
Logging: jquery.dropotron.min.js in static/scripts directory
Logging: main.js in static/scripts directory
Client Console Output - Navigating to Route '/' with NuxtLink
Logging: rerunJs.js in middleware directory
Client based middleware
Print context.app.head.script:
Array(7) [ {…}, {…}, {…}, {…}, {…}, {…}, {…} ]
解决方案
要重新运行外部JavaScript(即jQuery),当使用 NuxtLink 导航到另一个页面并且 Nuxt 设置为通用模式时,将使用两个生命周期挂钩。
首先,中间件应该从 head 中删除脚本。可以肯定的是,只有客户端会删除脚本。在初始页面加载时,中间件基于服务器和脚本 运行,即使不触发它们也是如此。
middleware/rerunJs.js
...
if (process.client) {
context.app.head.script = undefined
}
...
之后,所需页面的 mounted-Hook 应将脚本附加到正文的头部和末尾。
pages/index.vue
...
mounted () {
(function LoadMyJs () {
const docHeadObj = document.getElementsByTagName('head')[0]
const jqueryScript = document.createElement('script')
jqueryScript.outerHTML = '<scr' + 'ipt data-n-head="ssr" src="/scripts/jquery.min.js" data-body="true">' + ' </scr' + 'ipt>'
jqueryScript.src = '/scripts/jquery.min.js'
jqueryScript.defer = true
docHeadObj.appendChild(jqueryScript)
document.body.innerHTML = document.body.innerHTML + queryScript.outerHTML
}())
}
...