import * as esbuild from "esbuild"; import { build } from "esbuild"; import { globSync } from "glob"; import { execa } from "execa"; import fs from "node:fs"; import { fileURLToPath } from "node:url"; import { dirname } from "node:path"; const _filename = fileURLToPath(import.meta.url); const _dirname = dirname(_filename); const _package = JSON.parse(fs.readFileSync(_dirname + '/package.json', 'utf-8')); const entryPoints = globSync("./src/**/**.{ts,tsx}"); /** @type {import('esbuild').BuildOptions} */ const options = { entryPoints, minify: process.env.NODE_ENV === 'production', outdir: "./built", target: "es2022", platform: "browser", format: "esm", sourcemap: 'linked', }; // built配下をすべて削除する fs.rmSync('./built', { recursive: true, force: true }); if (process.argv.map(arg => arg.toLowerCase()).includes("--watch")) { await watchSrc(); } else { await buildSrc(); } async function buildSrc() { console.log(`[${_package.name}] start building...`); await build(options) .then(it => { console.log(`[${_package.name}] build succeeded.`); }) .catch((err) => { process.stderr.write(err.stderr); process.exit(1); }); if (process.env.NODE_ENV === 'production') { console.log(`[${_package.name}] skip building d.ts because NODE_ENV is production.`); } else { await buildDts(); } console.log(`[${_package.name}] finish building.`); } function buildDts() { return execa( 'tsc', [ '--project', 'tsconfig.json', '--outDir', 'built', '--declaration', 'true', '--emitDeclarationOnly', 'true', ], { stdout: process.stdout, stderr: process.stderr, } ); } async function watchSrc() { const plugins = [{ name: 'gen-dts', setup(build) { build.onStart(() => { console.log(`[${_package.name}] detect changed...`); }); build.onEnd(async result => { if (result.errors.length > 0) { console.error(`[${_package.name}] watch build failed:`, result); return; } await buildDts(); }); }, }]; console.log(`[${_package.name}] start watching...`) const context = await esbuild.context({ ...options, plugins }); await context.watch(); await new Promise((resolve, reject) => { process.on('SIGHUP', resolve); process.on('SIGINT', resolve); process.on('SIGTERM', resolve); process.on('SIGKILL', resolve); process.on('uncaughtException', reject); process.on('exit', resolve); }).finally(async () => { await context.dispose(); console.log(`[${_package.name}] finish watching.`); }); }