feat(@vant/cli): using esbuild to transform script (#10143)

* feat(@vant/cli): using esbuild to transform script

* chore: update babel doc

* chore: update lock

* chore: update

* fix: format
This commit is contained in:
neverland
2022-01-06 14:47:28 +08:00
committed by GitHub
parent 7b214cb87c
commit 1890cf6607
10 changed files with 67 additions and 1046 deletions
+10 -7
View File
@@ -1,6 +1,6 @@
import fse from 'fs-extra';
import execa from 'execa';
import { join, relative } from 'path';
import fse from 'fs-extra';
import { clean } from './clean.js';
import { CSS_LANG } from '../common/css.js';
import { ora, consola } from '../common/logger.js';
@@ -27,12 +27,13 @@ import {
setModuleEnv,
setBuildTarget,
} from '../common/index.js';
import type { Format } from 'esbuild';
const { remove, copy, readdir, existsSync } = fse;
async function compileFile(filePath: string) {
async function compileFile(filePath: string, format: Format) {
if (isScript(filePath)) {
return compileScript(filePath);
return compileScript(filePath, format);
}
if (isStyle(filePath)) {
return compileStyle(filePath);
@@ -69,12 +70,14 @@ async function preCompileDir(dir: string) {
);
}
async function compileDir(dir: string) {
async function compileDir(dir: string, format: Format) {
const files = await readdir(dir);
await Promise.all(
files.map((filename) => {
const filePath = join(dir, filename);
return isDir(filePath) ? compileDir(filePath) : compileFile(filePath);
return isDir(filePath)
? compileDir(filePath, format)
: compileFile(filePath, format);
})
);
}
@@ -86,13 +89,13 @@ async function copySourceCode() {
async function buildESMOutputs() {
setModuleEnv('esmodule');
setBuildTarget('package');
await compileDir(ES_DIR);
await compileDir(ES_DIR, 'esm');
}
async function buildCJSOutputs() {
setModuleEnv('commonjs');
setBuildTarget('package');
await compileDir(LIB_DIR);
await compileDir(LIB_DIR, 'cjs');
}
async function buildTypeDeclarations() {
+9 -27
View File
@@ -14,6 +14,7 @@ export const TEST_REGEXP = new RegExp('\\' + sep + 'test$');
export const ASSET_REGEXP = /\.(png|jpe?g|gif|webp|ico|jfif|svg|woff2?|ttf)$/i;
export const STYLE_REGEXP = /\.(css|less|scss)$/;
export const SCRIPT_REGEXP = /\.(js|ts|jsx|tsx)$/;
export const JSX_REGEXP = /\.(j|t)sx$/;
export const ENTRY_EXTS = ['js', 'ts', 'tsx', 'jsx', 'vue'];
export function removeExt(path: string) {
@@ -46,33 +47,14 @@ export function getComponents() {
);
}
export function isDir(dir: string) {
return lstatSync(dir).isDirectory();
}
export function isDemoDir(dir: string) {
return DEMO_REGEXP.test(dir);
}
export function isTestDir(dir: string) {
return TEST_REGEXP.test(dir);
}
export function isAsset(path: string) {
return ASSET_REGEXP.test(path);
}
export function isSfc(path: string) {
return SFC_REGEXP.test(path);
}
export function isStyle(path: string) {
return STYLE_REGEXP.test(path);
}
export function isScript(path: string) {
return SCRIPT_REGEXP.test(path);
}
export const isDir = (dir: string) => lstatSync(dir).isDirectory();
export const isDemoDir = (dir: string) => DEMO_REGEXP.test(dir);
export const isTestDir = (dir: string) => TEST_REGEXP.test(dir);
export const isAsset = (path: string) => ASSET_REGEXP.test(path);
export const isSfc = (path: string) => SFC_REGEXP.test(path);
export const isStyle = (path: string) => STYLE_REGEXP.test(path);
export const isScript = (path: string) => SCRIPT_REGEXP.test(path);
export const isJsx = (path: string) => JSX_REGEXP.test(path);
const camelizeRE = /-(\w)/g;
const pascalizeRE = /(\w)(\w*)/g;
@@ -1,36 +1,56 @@
import fse from 'fs-extra';
import babel from '@babel/core';
import esbuild, { type Format } from 'esbuild';
import { sep } from 'path';
import { transformAsync } from '@babel/core';
import { replaceExt } from '../common/index.js';
import { isJsx, replaceExt } from '../common/index.js';
import { replaceCSSImportExt } from '../common/css.js';
import { replaceScriptImportExt } from './get-deps.js';
const { readFileSync, removeSync, outputFileSync } = fse;
export async function compileScript(filePath: string): Promise<void> {
return new Promise((resolve, reject) => {
if (filePath.includes('.d.ts')) {
resolve();
return;
export async function compileScript(
filePath: string,
format: Format
): Promise<void> {
if (filePath.includes('.d.ts')) {
return;
}
let code = readFileSync(filePath, 'utf-8');
if (!filePath.includes(`${sep}style${sep}`)) {
code = replaceCSSImportExt(code);
}
code = replaceScriptImportExt(code, '.vue', '');
if (isJsx(filePath)) {
const babelResult = await babel.transformAsync(code, {
filename: filePath,
babelrc: false,
presets: ['@babel/preset-typescript'],
plugins: [
[
'@vue/babel-plugin-jsx',
{
enableObjectSlots: false,
},
],
],
});
if (babelResult?.code) {
({ code } = babelResult);
}
}
let code = readFileSync(filePath, 'utf-8');
if (!filePath.includes(`${sep}style${sep}`)) {
code = replaceCSSImportExt(code);
}
code = replaceScriptImportExt(code, '.vue', '');
transformAsync(code, { filename: filePath })
.then((result) => {
if (result) {
const jsFilePath = replaceExt(filePath, '.js');
removeSync(filePath);
outputFileSync(jsFilePath, result.code);
resolve();
}
})
.catch(reject);
const esbuildResult = await esbuild.transform(code, {
loader: 'ts',
target: 'es2016',
format,
});
({ code } = esbuildResult);
const jsFilePath = replaceExt(filePath, '.js');
removeSync(filePath);
outputFileSync(jsFilePath, code);
}