背景:我这边尝试使用husky+自动node实现提交的同时,自动把本地代码复制粘贴到项目目录中。 使用了docker+pm2+fs-extra+child_process 其他部分代码与上一篇文章对应,是同一个项目中的
创建dockerfile
本来使用了最新的node:latest(17.几的测试版),然后yarn报错,这边降了版本
FROM node:16
RUN yarn global add tyarn \
&& tyarn global add pm2
WORKDIR /home/project
EXPOSE 3000
CMD ["pm2-runtime","ecosystem.config.js"]
PM2使用pm2-runtime因为docker中会监听前台任务,如果什么都没就会退出。而默认的pm2命令在后台运行,docker无法监听到。
.husky>pre-commit
#!/bin/sh
. "$(dirname "$0")/_/husky.sh"
# npm test
npm run move:prod
package.json
"scripts": {
"start": "nodemon ./index.js",
"prepare": "husky install",
"move:prod": "node ./bin/moveFile.js"
},
ecosystem.config.js
console.log("读取配置文件", __dirname)
module.exports = {
apps: [
{
name: "back",
script: "index.js",
out_file: "./logs/back.log",
error_file: "./logs/err.log",
watch: true,
ignore_watch: [
"node_modules",
"logs",
"uploads",
".git",
"static",
"test"
],
"watch_options": {
"usePolling": true
}
}
],
// 这一块内容可能没有成功执行,以后再进行二次调试,目前看不出什么问题(因为没有日志输出,但程序正常,无法判断是否有问题)
deploy: {
production: {
'post-deploy': "tyarn && pm2 startOrRestart ecosystem.config.js"
}
}
}
bin/moveFile.js
// @ts-nocheck
const { execSync, exec } = require('child_process')
const { emptyDir, copy } = require('fs-extra')
const { readdir } = require('fs/promises')
const path = require('path')
// 文件路径
// 打包路径
const source = path.resolve(__dirname, '../')
const target = path.resolve(__dirname, '../../docker-data/back/project')
const history = path.resolve(__dirname, '../../docker-data/back/history')
const ignoreCopy = ['node_modules', '.git', '.husky', 'bin']
async function main() {
try {
// 启停docker,否则复制粘贴文件出问题
execSync("docker stop visual_back")
await copyDir(target, history)
await copyDir(source, target)
execSync("docker start visual_back")
} catch (e) {
throw new Error(e)
}
}
async function copyDir(source, target) {
// 遍历文件,然后选择性复制
let files = await readdir(source)
let promiseList = []
for (let file of files) {
// 如果不在忽略列表
if (!ignoreCopy.includes(file)) {
// 需要放置到的后端
let targetTemp = path.resolve(target, file)
// 源文件
let sourceTemp = path.resolve(source, file)
// 放入Promise集合
promiseList.push(copy(sourceTemp, targetTemp))
}
}
await Promise.all(promiseList)
console.log(source + "-->" + target + '。文件处理完成')
}
main()
这边在移动文件的时候,必须先停止docker相应的容器,不然会报错。 关于文件删除后,对应的迁移文件夹是不会删除文件的,这一点需要特别注意。 其实有一个办法,先删除所有ignoreCopy和ignoreDelete(这个未实现)除外的所有文件,再进行拷贝。不过懒得写了,而且自己搭着玩并不重要