From 6a895d68578c7ecf1739ebcb3f97d9d4fabc5125 Mon Sep 17 00:00:00 2001 From: Harry Chen Date: Mon, 12 Feb 2024 22:13:51 +0800 Subject: [PATCH] chore: add colors --- lib/index.js | 84 +++++++++++++++++++++++++++------------------------- lib/util.js | 51 +++++++++++++++++++++++++++++++ 2 files changed, 95 insertions(+), 40 deletions(-) diff --git a/lib/index.js b/lib/index.js index e73b7df..9ba548f 100644 --- a/lib/index.js +++ b/lib/index.js @@ -6,6 +6,8 @@ const { deleteFolderRecursive, readJSONCFile, copyFilesRecursive, + output, + colors, } = require('./util'); const path = require('path'); const fs = require('fs'); @@ -71,6 +73,31 @@ function run() { const restart = debounce(() => { runChild && runChild.restart(); }, 1000); + + + function onFileChange(p) { + // 这里使用了标识来判断是否编译成功,理论上会有时序问题,但是本质上事件还是同步执行的,测试下来感觉没有问题 + if (!isCompileSuccess) return; + output(`${colors.dim('File ')}${p}${colors.dim(' has been changed')}`, true); + // 单个文件的 tsc alias 替换 + if (hasPaths) { + // const filePath = path.join(outDir, p); + // const fileContents = fs.readFileSync(filePath, 'utf8'); + // const newContents = runFile({fileContents, filePath}); + // // 回写内容 + // fs.writeFileSync(filePath, newContents, 'utf8'); + + // 这里使用全量替换,tsc 增量编译会把老文件修改回去 + replaceTscAliasPaths({ + configFile: tsconfigPath, + outDir, + }); + // 避免重复触发文件变化 + isCompileSuccess = false; + } + // 单个文件的 hot reload 处理 + restart(); + } // 启动执行 tsc 命令 const child = forkTsc(tscArgs, { @@ -96,18 +123,18 @@ function run() { runChild.onServerReady( async (serverReportOption, isFirstCallback, during) => { if (isFirstCallback) { - console.log( - `\x1B[32mNode.js server\x1B[0m \x1B[2mstarted in\x1B[0m ${during} ms\n` + output( + `${colors.green('Node.js server')} ${colors.dim('started in')} ${during} ms\n` ); if (serverReportOption && serverReportOption.port) { const protocol = serverReportOption.ssl ? 'https' : 'http'; - console.log( - `\x1B[32m➜\x1B[0m Local: \x1B[36m${protocol}://127.0.0.1:\x1B[1m${serverReportOption.port}/ \x1B[0m` + output( + `${colors.green('➜')} Local: ${colors.cyan(`${protocol}://127.0.0.1:${colors.bright(serverReportOption.port)}${colors.cyan('/')}`)} ` ); const netWorkIp = getIp(); if (netWorkIp) { - console.log( - `\x1B[32m➜\x1B[0m \x1B[2mNetwork: ${protocol}://${netWorkIp}:${serverReportOption.port}/ \x1B[0m` + output( + `${colors.green('➜')} ${colors.dim(`Network: ${protocol}://${netWorkIp}:${serverReportOption.port}/ `)}` ); } console.log(''); @@ -123,51 +150,28 @@ function run() { }); fileDeleteWatcher - .on('unlink', path => { - console.log(`File ${path} has been removed`) + .on('unlink', p => { + const filePath = path.join(cwd, outDir, p.replace(/\.ts$/, '.js')); + if (fs.existsSync(filePath)) { + fs.unlinkSync(filePath); + output(`File ${path} has been removed`) + } }) - .on('unlinkDir', path => { - console.log(`Directory ${path} has been removed`) + .on('unlinkDir', p => { + console.log(`Directory ${p} has been removed`) }); fileChangeWatcher = chokidar.watch('**/**.js', { cwd: path.join(cwd, outDir), }); - const runFile = await prepareSingleFileReplaceTscAliasPaths({ - configFile: tsconfigPath, - outDir, - }); - - fileChangeWatcher.on('change', p => { - // 这里使用了标识来判断是否编译成功,理论上会有时序问题,但是本质上事件还是同步执行的,测试下来感觉没有问题 - if (!isCompileSuccess) return; - console.log(`File ${p} has been changed`) - // 单个文件的 tsc alias 替换 - if (hasPaths) { - const filePath = path.join(outDir, p); - const fileContents = fs.readFileSync(filePath, 'utf8'); - const newContents = runFile({fileContents, filePath}); - // 回写内容 - fs.writeFileSync(filePath, newContents, 'utf8'); - // 避免重复触发文件变化 - isCompileSuccess = false; - } - // 单个文件的 hot reload 处理 - restart(); - }); - + fileChangeWatcher.on('change', onFileChange); } } else { - // 输出当前时间 HH:mm:ss - const now = new Date(); - const timeStr = `${now.getHours()}:${now.getMinutes()}:${now.getSeconds()}`; - console.log( - `[\x1B[2m${timeStr}\x1B[0m] \x1B[32mNode.js server\x1B[0m \x1B[2mrestarted in\x1B[0m ${during} ms\n` + output( + `${colors.green('Node.js server')} ${colors.dim('restarted in')} ${during} ms\n` ); } - - } ); } diff --git a/lib/util.js b/lib/util.js index 6f2506f..8ce7474 100644 --- a/lib/util.js +++ b/lib/util.js @@ -180,3 +180,54 @@ exports.copyFilesRecursive = function (sourceDir, targetDir, allowJS) { fs.copyFileSync(sourceFile, targetFile); } }; + +exports.colors = function getConsoleColors() { + const format = { + reset: "\x1b[0m", + bright: "\x1b[1m", + dim: "\x1b[2m", + underscore: "\x1b[4m", + blink: "\x1b[5m", + reverse: "\x1b[7m", + hidden: "\x1b[8m", + + black: "\x1b[30m", + red: "\x1b[31m", + green: "\x1b[32m", + yellow: "\x1b[33m", + blue: "\x1b[34m", + magenta: "\x1b[35m", + cyan: "\x1b[36m", + white: "\x1b[37m", + + bgBlack: "\x1b[40m", + bgRed: "\x1b[41m", + bgGreen: "\x1b[42m", + bgYellow: "\x1b[43m", + bgBlue: "\x1b[44m", + bgMagenta: "\x1b[45m", + bgCyan: "\x1b[46m", + bgWhite: "\x1b[47m" + }; + + const colors = {}; + for (const color in format) { + colors[color] = (text) => `${format[color]}${text}${format.reset}`; + } + return colors; +}(); + +exports.output = function (msg, datePadding = false) { + let timeStr = ''; + if (datePadding) { + // 输出当前时间 HH:mm:ss + const now = new Date(); + timeStr = `[${exports.colors.dim(`${now.getHours()}:${now.getMinutes()}:${now.getSeconds()}`)}]`; + console.log( + `${timeStr} ${msg}` + ); + return; + } + + console.log(msg); +} \ No newline at end of file