fizz-cli
Version:
fizz项目脚手架
166 lines (159 loc) • 4.79 kB
JavaScript
#!/usr/bin/env node
// 交互式命令行
const inquirer = require("inquirer");
// 命令行 loading 效果
const ora = require("ora");
// shell
const shell = require("shelljs");
// git
const clone = require("git-clone");
// 修改控制台字符串的样式
const chalk = require("chalk");
// 文件系统
const fs = require("fs");
// path模块,可以生产相对和绝对路径
const path = require("path");
// 仓库地址、默认分支
const { respository, defaultBranch } = require("../config");
// 项目路径
const projectPath = shell.pwd().toString();
// 备份目录
const backupPath = path.join(projectPath, "_backups");
// 不需要备份的文件夹
const foldersNotBackup = [
"node_modules",
".git",
".svn",
"dist",
"_backups",
"_temp",
];
// 不需要更新的文件夹
const foldersNotUpdate = ["app"];
// 不需要更新的文件
const filesNotUpdate = [".env.debug", ".env.debug.local", "fizz.config.js"];
// 更新临时目录
const tempPath = path.join(projectPath, "_temp");
module.exports = function () {
console.log("\n项目框架更新");
console.log(
chalk.bold.yellow("\n建议在更新前提交一次代码,避免发生意外导致代码丢失\n")
);
inquirer
.prompt([
{
name: "ready",
type: "confirm",
message: "确认开始更新?",
},
])
.then(({ ready }) => {
if (ready) {
return inquirer.prompt([
{
name: "frameworkType",
type: "list",
message: "请选择框架版本",
choices: ["fizz", "fizz-ie8"],
},
]);
}
})
.then(({ frameworkType }) => {
if (frameworkType) {
start(frameworkType);
}
});
};
/**
* 备份文件
*/
function backup() {
// 删除此前的备份目录
shell.rm("-rf", backupPath);
// 重新创建备份目录
shell.mkdir(backupPath);
// 获取项目目录下所有文件夹及文件
const files = fs.readdirSync(projectPath);
// 遍历项目目录
files.forEach((filename) => {
const stats = fs.statSync(path.join(projectPath, filename));
// 处理文件
if (stats.isFile()) {
// 备份根目录下所有文件
shell.cp("-f", path.join(projectPath, filename), backupPath);
// 为了能够同步远程仓库删掉的文件,备份完成后将文件从项目目录中删除
// 对于不需要更新的文件不用删除,后续更新时不会覆盖这些文件
if (!filesNotUpdate.includes(filename)) {
shell.rm("-rf", path.join(projectPath, filename));
}
}
// 处理文件夹
else if (stats.isDirectory() && !foldersNotBackup.includes(filename)) {
// 只备份需要备份的文件夹
shell.cp("-rf", path.join(projectPath, filename), backupPath);
// 为了能够同步远程仓库删掉的文件夹,备份完成后将文件夹从项目目录中删除
// 对于不需要更新的文件夹不用删除,后续更新时不会覆盖这些文件夹
if (!foldersNotUpdate.includes(filename)) {
shell.rm("-rf", path.join(projectPath, filename));
}
}
});
}
/**
* 更新文件
*/
function update() {
// 获取临时目录下所有文件夹及文件
const files = fs.readdirSync(tempPath);
// 遍历临时目录(临时目录中是从远程仓库拉下来的模板代码)
files.forEach((filename) => {
const stats = fs.statSync(path.join(tempPath, filename));
// 过滤出需要更新的根目录文件
if (stats.isFile() && !filesNotUpdate.includes(filename)) {
// 将临时目录下的文件复制到项目目录中
shell.cp("-rf", path.join(tempPath, filename), projectPath);
}
// 过滤出需要更新的文件夹
else if (
stats.isDirectory() &&
!foldersNotBackup.includes(filename) &&
!foldersNotUpdate.includes(filename)
) {
// 将临时目录下的文件复制到项目目录中
shell.cp("-rf", path.join(tempPath, filename), projectPath);
}
});
// 清除本地临时目录
shell.rm("-rf", tempPath);
}
/**
* 开始更新
* @param {string} branch 分支名称
*/
function start(frameworkType) {
console.log("----------------------------------");
const spinner = ora(`正在备份文件...`);
spinner.start();
// 备份文件
backup();
spinner.succeed();
spinner.text = "正在获取更新...";
spinner.start();
clone(
respository[frameworkType],
tempPath,
{
checkout: defaultBranch[frameworkType],
},
function () {
spinner.succeed();
spinner.text = `更新中...`;
spinner.start();
// 更新文件
update();
spinner.succeed();
console.log(chalk.greenBright("\n框架升级完成!"));
}
);
}