
编译less文件
script部分的编译比较复杂,我们最后再看,先看一下less文件的处理。
// varlet-cli/src/compiler/compileStyle.ts
import { render } from 'less'
export async function compileLess(file: string) {
const source = readFileSync(file, 'utf-8')
const { css } = await render(source, { filename: file })
writeFileSync(replaceExt(file, '.css'), clearEmptyLine(css), 'utf-8')
}
很简单,使用less包将less编译成css,然后写入文件即可,到这里又生成了一个css文件:

编译script文件
script部分,主要是ts、tsx文件,Varlet大部分组件是使用Vue单文件编写的,不过也有少数组件使用的是tsx,编译调用了compileScriptFile方法:
// varlet-cli/src/compiler/compileScript.ts
export async function compileScriptFile(file: string) {
const sources = readFileSync(file, 'utf-8')
await compileScript(sources, file)
}
读取文件,然后调用compileScript方法,前面Vue单文件中解析出来的script部分内容调用的也是这个方法。
兼容模块导入
// varlet-cli/src/compiler/compileScript.ts
export async function compileScript(script: string, file: string) {
const modules = process.env.BABEL_MODULE
// 兼容模块导入
if (modules === 'commonjs') {
script = moduleCompatible(script)
}
// ...
}
首先针对commonjs做了一下兼容处理:
// varlet-cli/src/compiler/compileScript.ts
export const moduleCompatible = (script: string): string => {
const moduleCompatible = get(getVarletConfig(), 'moduleCompatible', {})
Object.keys(moduleCompatible).forEach((esm) => {
const commonjs = moduleCompatible[esm]
script = script.replace(esm, commonjs)
})
return script
}
替换一些导入语句,Varlet组件开发是基于ESM规范的,使用其他库时导入的肯定也是ESM版本,所以编译成commonjs模块时需要修改成对应的commonjs版本,Varlet引入的第三方库不多,主要就是dayjs:

使用babel编译
继续compileScript方法:
// varlet-cli/src/compiler/compileScript.ts
import { transformAsync } from '@babel/core'
export async function compileScript(script: string, file: string) {
// ...
// 使用babel编译js
let { code } = (await transformAsync(script, {
filename: file,// js内容对应的文件名,babel插件会用到
})) as BabelFileResult
// ...
}
接下来使用@babel/core包编译js内容,transformAsync方法会使用本地的配置文件,因为打包命令是在varlet-ui/目录下运行的,所以babel会在这个目录下寻找配置文件:

编译成module还是commonjs格式的判断也在这个配置中,有关配置的详解,有兴趣的可以阅读最后的附录小节。
提取样式导入语句
继续compileScript方法:
// varlet-cli/src/compiler/compileScript.ts
export const REQUIRE_CSS_RE = /(?