【开发笔记】VuePress 2 那些编译起来的奇怪事
为了获得主题颜色暗模式(Dark Mode)的支援,最近把使用很久的 VuePress 从 1.0 更新到 2.0 RC。虽然 2.0 RC 不是最终版本,但是预计未来底层架构的更动应该不会有太大的变化,既然早晚都是要更新的,所以就这样壮烈的入了坑...
Cannot use import statement outside a module
说壮烈或许有点夸大。不过最大的困扰,就是别人的解方通通不适用于自己的情况。从错误的提示,会让人单纯以为是 CommonJS vs ES6 的问题。所以试过在 package.json 中加上 "type": "module",也调整过副档名(extension)从 .js 变成 .mjs。甚至受到影响的 module,也尝试过把源码结构在引入时,从 import ... from 改成 const ... require。而在输出的部分,也从 export ... 改成 module.exports。
// 修改前(ES6)
import { ... } from './...';
...
..
.
export default { ... };
// 修改后(CommonJS)
const { ... } = require('./...');
...
..
.
module.exports = { ... };
没有意外,以上的尝试通通都没有顺利地解决问题,不然这篇笔记也不用写了。最后是把默认的 bundler 从 vite 改成 webpack 才获得解决。不过 vuepress 使用 webpack 做 bundler 需要在 config.js 内做额外的设定。另外,整个专案编译所需的时间也因此增加了不少。
import { webpackBundler } from '@vuepress/bundler-webpack'
export default defineUserConfig({
...,
bundler: webpackBundler({
postcss: {},
vue: {},
}),
...,
}
$router 组件外取值
在组件内或是 .vue 中来说,我们要取得路由的查询参数只要 $router.currentRoute.query 就可以了。但是组件外,例如 markdown 文件中要取得查询参数,则需要做一点小小变化 $router.currentRoute.value.query 才行。算是附带一提的小插曲。
留意 ref 对象的存在有可能是浮动的
最后这点就真的很烧脑了。过程中无论是开发环境或是生产环境,编译时都没有出现任何错误提示,实际在操作上也没有任何异常。不过部署后整合测试却通过不了。深究其原因发现 $ref 参照的对象调用得太早,此时元件对象还没有真正地生成被加到页面中,导致 focus 无法被设置到不存在的输入元件。目前是在调用 focus 时,刻意加上延迟来获得解决。
<template>
...
<input ref="search" ... />
...
</template>
<scripts>
...
mounted() {
// 加上一个延迟来确保 ref 对象存在
setTimeout(() => {
this.setFocusInput();
}, 600);
},
methods: {
setFocusInput() {
const search = this.$refs.search;
// 需要检查 ref 和 element 可能为 undefined
if (!search || !search.$el) {
return;
}
search.$el.focus();
}
}
...
</scripts>