美文网首页
前端自动化部署

前端自动化部署

作者: 懿小诺 | 来源:发表于2019-10-14 10:10 被阅读0次

    之前写项目在测试环境打包步骤为:打包,将dist内的文件拖拽到测试服务器上。这个过程比较麻烦,为了能简便一些,实现自动部署,我查了一下资料,较为简便的方法如下:

    1.在package.json包中引入下面三个模块插件:ssh2、commander、archiver

    也可以用命令行分别安装

    npm install ssh2 --save 实现自动化上传

    npm install commander --save 简化实现命令流程

    npm install archiver --save 压缩工具-用来压缩文件


    image

    2.在config/prod.env.js进行如下配置:

    包括服务器名称,账号,密码,项目名称(上传的文件夹名称),路径(上传路径)

    
    "use strict";
    
    const REMOTE_SERVER = '0.0.0.0'
    
    const DEFAULT_HOST = {host: REMOTE_SERVER, user: 'xxx', password: 'xxx', key: '', name: 'xxx', path: '/home/tbc/smart_car/webapps'}
    
    module.exports = {
    
        NODE_ENV: '"production"',
    
        REMOTE_HOST: REMOTE_SERVER,
    
        DEFAULT_HOST: DEFAULT_HOST,
    
    };
    
    

    3.修改buiild/build.js文件

    在文件中引入一个commander,并给其配置参数,在最后对program.publish进行了判断,若存在则引入publish/publish-zip文件。到这一步为止,如果输入了npm run publish,这会完成相应的打包工作,并且引入了publish/publish-zip文件

    image image
    'use strict'
    require('./check-versions')()
    const program = require('commander')
    //解析当前执行的命令行
    var minimist = require('minimist')
    let env = minimist(process.argv).env
    console.log(env);
    if (env === 'test') {
      process.env.NODE_ENV = 'testing'
      process.env.npm_config_report = true
    }else {
      process.env.NODE_ENV = 'production'
    }
    console.log("process.env.NODE_ENV="+process.env.NODE_ENV);
    
    const ora = require('ora')
    const rm = require('rimraf')
    const path = require('path')
    const chalk = require('chalk')
    const webpack = require('webpack')
    const config = require('../config')
    const webpackConfig = require('./webpack.prod.conf')
    
    const spinner = ora('building for production...')
    spinner.start()
    program
      .version('0.0.1')
      .option('-p, --publish', 'Publish Remote')
      .parse(process.argv)
    rm(path.join(config.build.assetsRoot, config.build.assetsSubDirectory), err => {
      if (err) throw err
      webpack(webpackConfig, (err, stats) => {
        spinner.stop()
        if (err) throw err
        process.stdout.write(stats.toString({
          colors: true,
          modules: false,
          children: false, // If you are using ts-loader, setting this to true will make TypeScript errors show up during build.
          chunks: false,
          chunkModules: false
        }) + '\n\n')
    
        if (stats.hasErrors()) {
          console.log(chalk.red('  Build failed with errors.\n'))
          process.exit(1)
        }
    
        console.log(chalk.cyan('  Build complete.\n'))
        console.log(chalk.yellow(
          '  Tip: built files are meant to be served over an HTTP server.\n' +
          '  Opening index.html over file:// won\'t work.\n'
        ))
       
        if (program.publish) {
          console.log('-----');
          require('../publish/publish-zip')()
        }
        
      })
    })
    
    

    4.在根目录下创建publish文件夹,在publish内创建publish-zip文件,提供压缩方法.压缩完成后引入publish.js文件

    文件内容如下:

    
    const fs = require('fs')
    
    const archiver = require('archiver')
    
    const env = require('../config/prod.env')
    
    // const chalk = require('chalk')
    
    module.exports = function () {
    
    //   console.log(chalk.cyan('  Zip files.\n'))
    
    //   console.time('key')
    
      var output = fs.createWriteStream(`publish/${env.DEFAULT_HOST.name}.zip`)
    
      var archive = archiver('zip')
    
      output.on('close', function () {
    
        // console.log(chalk.cyan('  Zip files.\n'))
    
        // console.timeEnd('key')
    
        console.log('compress completed...ready upload')
    
        require('./publish.js')()
    
      })
    
      output.on('end', function () {
    
      })
    
      archive.on('error', function (err) {
    
        throw err
    
      })
    
      archive.pipe(output)
    
      archive.glob('./dist' + '/**')
    
      archive.finalize()
    
    }
    
    

    5.在publish文件夹内创建publish.js用来上传文件、删除文件

    代码如下:

    
    const env = require('../config/prod.env')
    
    const chalk = require('chalk')
    
    var Client = require('ssh2').Client
    
    var conn = new Client()
    
    var fs = require('fs')
    
    const user = {
    
      host: env.DEFAULT_HOST.host,
    
      port: 20022,
    
      username: env.DEFAULT_HOST.user,
    
      password: env.DEFAULT_HOST.password
    
    }
    
    /**
    
     * 1.进入目录
    
     * 2.删除旧的备份项目
    
     * 3.将原项目名称加上bak标志为备份文件
    
     * 4.解压缩上传的zip文件并将名称改为项目名称
    
     * 5.删除zip文件
    
     * 6.退出
    
     * @type {string[]}
    
     */
    
    const uploadShellList = [
    
      `cd ${env.DEFAULT_HOST.path}\n`,
    
      `rm -rf ${env.DEFAULT_HOST.name}.bak\n`,
    
      `mv ${env.DEFAULT_HOST.name} ${env.DEFAULT_HOST.name}.bak\n`,
    
      `unzip ${env.DEFAULT_HOST.name}.zip\n`,
    
      `mv dist ${env.DEFAULT_HOST.name}\n`,
    
      `rm -rf ${env.DEFAULT_HOST.name}.zip\n`,
    
      `exit\n`
    
    ]
    
    const params = {file: `./publish/${env.DEFAULT_HOST.name}.zip`, target: `${env.DEFAULT_HOST.path}/${env.DEFAULT_HOST.name}.zip`}
    
    /**
    
     * 上传文件
    
     * @param conn
    
     * @param params
    
     * @constructor
    
     */
    
    function UploadFile (conn, params) {
    
      const file = params.file
    
      const target = params.target
    
      if (!conn) {
    
        return
    
      }
    
      conn.sftp(function (err, sftp) {
    
        if (err) {
    
          throw err
    
        }
    
        sftp.fastPut(file, target, {}, function (err, result) {
    
          if (err) {
    
            console.log(chalk.red(err.message))
    
            throw err
    
          }
    
          Shell(conn)
    
        })
    
      })
    
    }
    
    function Ready () {
    
      conn.on('ready', function () {
    
        console.log('Client :: ready')
    
        UploadFile(conn, params)
    
      }).connect(user)
    
    }
    
    /**
    
     * 上传完成后服务器需要执行的内容
    
     * 删除本地压缩文件
    
     * @param conn
    
     * @constructor
    
     */
    
    function Shell (conn) {
    
      conn.shell(function (err, stream) {
    
        if (err) throw err
    
        stream.on('close', function () {
    
          console.log('Stream :: close')
    
          conn.end()
    
          fs.unlinkSync(`./publish/${env.DEFAULT_HOST.name}.zip`)
    
        }).on('data', function (data) {
    
          console.log('STDOUT: ' + data)
    
        }).stderr.on('data', function (data) {
    
          console.log('STDERR: ' + data)
    
        })
    
        stream.end(uploadShellList.join(''))
    
      })
    
    }
    
    module.exports = function () {
    
      try {
    
        Ready()
    
      } catch (err) {
    
        console.log(err)
    
      }
    
    }
    
    

    6.更改打包部署指令

    在原来打包指令的基础上加了一个 -p

    通过监听这个参数,来判断是只进行打包还是打包上传

    image

    至此,自动部署已配置完成,通过 npm run publish即可自动打包部署啦!

    相关文章

      网友评论

          本文标题:前端自动化部署

          本文链接:https://www.haomeiwen.com/subject/qpilmctx.html