UNPKG

yl-bud

Version:

一览科技前端开发工具

376 lines (338 loc) 12.9 kB
#!/usr/bin/env node /* * @Author: xiaohu * @Date: 2018-06-21 12:00:35 * @Last Modified by: xiaohu.li * @Last Modified time: 2018-08-29 14:36:35 */ require('shelljs/global');//nodejs中使用shelljs模块的exec方法执行shell脚本命令 const fs = require('fs'); const path = require('path'); const co = require('co');//Generator 自驱动的流程处理库 var OSS = require('ali-oss'); const program = require('commander')//命令行处理框架 const thunkify = require('thunkify');//将多参数函数替换成单参数函数的转换器 const colors = require('cli-color');//改变控制台输出文本的颜色、文本格式化。 const inquirer = require('inquirer');//可嵌入式的命令行交互界面 const utils = require('../lib/utils'); const webServer = require('./../lib/server'); const appInfo = require('./../package.json'); const gitTools = utils.git; const execThunk = thunkify(exec); const LOGO = colors.xterm(20).bgXterm(226); const USERCONFIG = utils.getUserConfig; const BUILDINFOS = utils.getBuildInfo(USERCONFIG.version); var setConfigVersion = thunkify(function(version, callback) { var branch = version ? version : false; gitTools.setConfigVersionThunk(branch, function(err, config) { return callback(err, config); }); }); program .allowUnknownOption() //不报错误 .version(appInfo.version) .usage('FEDTools前端开发工具') .option('-q, --quiet', '安静模式') .option('-r, --react', '初始化react工程') .action(function() { console.log(LOGO(' _____ _____ ____ _____ _ ')); console.log(LOGO('| ___| ____| _ \\_ _|__ ___ | |___ ')); console.log(LOGO('| |_ | _| | | | || |/ _ \\ / _ \\| / __|')); console.log(LOGO('| _| | |___| |_| || | (_) | (_) | \\__ \\')); console.log(LOGO('|_| |_____|____/ |_|\\___/ \\___/|_|___/')); }) .parse(process.argv); program .command('dev') .alias('d') .description('进行开发') .option('-p, --port [type]', '监听端口', '3333') .action(function(cmd, options) { console.log(colors.green('开启开发者模式')); webServer.start({ port: program.args[0].port, queit: program.quiet }); gitTools.setConfigVersion(); // 检测git分支,设置config.version }).on('--help', function() { console.log(' 举个栗子:'); console.log(''); console.log(' bud dev,开启本地开发者模式'); console.log(' bud dev -p|--port [端口号] : 指定端口号'); console.log(''); process.exit(1); }); program .command('init') .alias('i') .description('初始化工程目录') .action(function(cmd, options) { console.log(colors.green('正在初始化工程目录ing...')); var dirname = path.join(process.cwd(), './');//当前目录 utils.fileGenerator.projectGenerator({ 'dirname': dirname, 'react': program.react }, function() { // 初始化常规工程 console.log(colors.blue('正在安装工程构建所需要的依赖模块...')); var initTime = new Date().getTime(); utils.fileGenerator.dependenciesGenerator({ // 复制依赖文件Node_modules 'dirname': dirname }, function(error) { var nowTime = new Date().getTime(); if (!error) { console.log(colors.green('依赖文件拷贝完成!'), colors.blue('共耗时:' + (nowTime - initTime) / 1000, 's')); } else { console.log(colors.red('拷贝依赖文件失败!'), colors.blue('共耗时:' + (nowTime - initTime) / 1000, 's')); console.log(colors.red(error)); } }); }); }).on('--help', function() { console.log(' 举个栗子:'); console.log(''); console.log(' bud init , 在当前路径下初始化[通用]工程目录'); console.log(''); process.exit(1); }); program .command('build') .alias('p') .description('进行构建') .action(function(cmd, options) { var deployJSON = null; // build.json源 var isPublish = false; // 是否构建后调用发布接口 var configure = {}; // 读取自本地工程config.json配置 co(function*() { try { configure = yield setConfigVersion(false); // 检测git分支,设置config.version,并返回新的分支 } catch (e) { console.log(colors.red('警告:当前不是git开发环境!')) } inquirer.prompt([{ type: 'input', name: 'username', message: '请输入您的用户名:' }, { type: 'list', name: 'env', message: '请选择发布环境:', choices: [ // { // name: '本地构建(相对路径构建,同时构建发布js、html)', // value: 'dev' // },{ // name: '日常发布(相对路径构建,同时构建发布js、html)', // value: 'daily' // }, { name: '预发发布(绝对路径构建,同时构建发布js、html)', value: 'pre' }, { name: '线上发布(相对路径构建,构建发布html)', value: 'production' }] //['本地生成部署配置', '日常环境', '预发环境', '线上环境'] }, { type: 'checkbox', name: 'selectedEntry', message: '请选择需要进行构建的页面:', choices: BUILDINFOS.autoGetHtml.keys }]).then(function(answers) { deployJSON = answers; deployJSON.htmlEntry = []; deployJSON.jsEntry = {}; deployJSON.appName = configure.appName; // 应用名 deployJSON.remotes = configure.remotes; // Git远端地址 deployJSON.version = configure.version; // Git分支版本 deployJSON.publish = configure.publish; // 发布配置信息 deployJSON.cdnhost = configure.cdnhost; // 静态资源cdn域名 deployJSON.oss = configure.oss; // oss信息 answers.selectedEntry.forEach(function(se, index) { // 生成发布列表,构建列表 for (var htmlKey in BUILDINFOS.autoGetHtml.jsEntry) { // console.log(htmlKey) if (htmlKey.split(se).length > 1) { var tmpSrc = './' + htmlKey + '.html'; if (configure.version) { tmpSrc = tmpSrc.replace(configure.version + '/', ''); } if (BUILDINFOS.autoGetHtml.jsEntry[htmlKey]) { deployJSON.jsEntry[htmlKey] = BUILDINFOS.autoGetHtml.jsEntry[htmlKey]; } deployJSON.htmlEntry.push(tmpSrc); break; } } }); // console.log(deployJSON) return deployJSON; }).then(function(data) { if (data.selectedEntry.length == 0) { return console.log(colors.red('没有选择任何页面,构建结束')); } co(function*() { var filename = path.join(utils.path.cwdPath, 'build.json'); var jsonData = JSON.stringify(data); try { fs.writeFileSync(filename, jsonData); console.log(colors.green('build.json创建成功')); } catch (err) { console.log(colors.red('build.json写入失败,请检查该文件')); console.log(colors.red(JSON.stringify(err))); } try { console.log('gulp deploy --entry ' + filename + ' --env '+ data.env) // yield execThunk('gulp deploy --entry ' + filename + ' --env daily'); // 在本地进行build yield execThunk('gulp deploy --entry ' + filename + ' --env '+ data.env); // 执行gulp构建任务 } catch (e) { console.log(colors.red('本地线上构建失败!')); console.log(e); } var chmod777 = function(callback) { var start777 = new Date().getTime(); var dir = data.env === 'production'?'./build':'./deploy'; exec('chmod -R 777 '+dir, { async: true, silent: program.quiet }, function(code, output) { var end777 = new Date().getTime(); console.log(colors.green('修改build权限777完成,共耗时:' + (end777 - start777) / 1000, 's')); }); } chmod777(); var cdnPublish = function(_path,filedir){ var client = new OSS({ accessKeyId: data.oss.accessKeyId, accessKeySecret: data.oss.accessKeySecret, region: data.oss.region }); co(function* () { // put from local file client.useBucket('yilantv'); var result = yield client.put(_path, filedir); }).catch(function (err) { console.log(err); }); } //文件遍历方法 var fileDisplay = function (filePath){ //根据文件路径读取文件,返回文件列表 fs.readdir(filePath,function(err,files){ if(err){ console.warn(err) }else{ //遍历读取到的文件列表 files.forEach(function(filename){ //获取当前文件的绝对路径 var filedir = path.join(filePath, filename); //根据文件路径获取文件信息,返回一个fs.Stats对象 fs.stat(filedir,function(eror, stats){ if(eror){ console.warn('获取文件stats失败'); }else{ var isFile = stats.isFile();//是文件 var isDir = stats.isDirectory();//是文件夹 if(isFile && path.extname(filedir) == '.js'){ // console.log(filedir); var _path = filedir.replace('deploy/javascripts/build/src/p','Transformers/'+data.appName) // console.log(_path); cdnPublish(_path,filedir) } if(isDir){ fileDisplay(filedir);//递归,如果是文件夹,就继续遍历该文件夹下面的文件 } } }) }); } }); } callbackFn = function(userName) { if (userName) { // 校验用户名 var serverType = '默认'; var doPublish = function(confArr) { var scpStartTime = new Date().getTime(); var $path = confArr.path; confArr.host.forEach(function(host) { // 'scp -r -P 5044 ./build root@47.93.14.55:/webroot/text' var dir = data.env === 'production'?'./build':'./deploy/html/build'; var scpCmd = 'scp -r -P 5044 '+dir+'/* root@' + host + ':' + $path +'/'+ USERCONFIG.appName console.log(scpCmd); exec(scpCmd, { async: true }, function(code, output) { var nowTime = new Date().getTime(); console.log(colors.green('已成功上传到 [' + serverType + '](' + host + ') 服务器!')); console.log(colors.blue('上传耗时:' + (nowTime - scpStartTime) / 1000, 's')); }); }); } try { if (data.env === 'daily') { // 发布日常 serverType = '日常'; // doPublish(USERCONFIG.publish.daily) } else if (data.env === 'pre') { // 发布预发阿里云 serverType = '预发'; fileDisplay('./deploy/javascripts'); doPublish(USERCONFIG.publish.pre) } else if (data.env === 'production') { // 发布线上服务器 serverType = '线上'; // doPublish(USERCONFIG.publish.production); } else { colors.yellow('发布未成功,因为您没有指定正确的发布环境'); } } catch (e) { console.log(colors.red('config.json发布配置错误,' + serverType + '发布失败')); console.log(colors.red(e)); } } else { console.log(colors.red('上传失败,无法解析您输入的userName')); } } callbackFn(data.username); console.log(colors.green('构建完毕!')); }); }); }); }).on('--help', function() { console.log(' 举个栗子:'); console.log(''); console.log('bud deploy'); console.log(''); process.exit(1); }); program .command('update') .alias('u') .description('更新工程构建所需要的依赖模块') .action(function(cmd, options) { console.log(colors.blue('开始更新工程构建所需要的依赖模块...')); var initTime = new Date().getTime(); var dirname = path.join(process.cwd(), './'); utils.fileGenerator.dependenciesGenerator({ // 复制依赖文件Node_modules 'dirname': dirname }, function(error) { var nowTime = new Date().getTime(); if (!error) { console.log(colors.green('依赖更新完成!'), colors.blue('共耗时:' + (nowTime - initTime) / 1000, 's')); } else { console.log(colors.red('拷贝依赖文件失败!'), colors.blue('共耗时:' + (nowTime - initTime) / 1000, 's')); console.log(colors.red(error)); } }); }).on('--help', function() { console.log(' 举个栗子:'); console.log(''); console.log(' bud update (-q|--quiet) , 更新bud全局依赖模块(开启安静模式,默认"非安静模式")'); console.log(' bud update -f [模块名], 强制重新安装bud指定依赖模块'); console.log(''); process.exit(1); }); program .command('help') .alias('h') .description('帮助') .action(function(cmd, options) { console.log('初始化 bud init'); console.log('启服务 bud dev 改端口号 -pxxxx'); console.log('构建 bud build'); }) program.parse(process.argv);