Jenkins 新增前端项目Job
指定运行的节点
选择部署运行的节点标签,dev标签对应开发环境
节点的远程命令执行配置
jenkins完整流程
配置源码 拉取
Credentials添加
触发远程构建
配置后可以支持远程触发jenkins构建(比如自建的CICD自动化发布平台),不需要远程构建的可以不配置
token生成配置
Build Steps
采用shell脚本模式
# jenkins服务Job运行的工作空间项目存放地址
codeRootDir="/data/jenkins/workspace/Dev.xx.Web"
# 项目部署远程服务器地址
remoteHost="10.30.222.11"
# 远程部署服务器存放镜像地址
remoteRootDir="/data/websites/images"
# 生成的项目镜像名称
dockerImageName="img.xx.web.dev"
# 运行的容器名称
containerName="xx.web.dev"
# 确保工作空间拥有该目录
mkdir -p ${codeRootDir}
# 切换到工作目录
cd ${codeRootDir}
echo build start
#指定镜像地址
npm config set registry https://registry.npmmirror.com/
#安装Vue项目依赖
npm install @vue/cli-plugin-eslint@latest --legacy-peer-deps
# 打包(根据Vue项目中的配置来)
npm run build
echo build end
echo "Building Docker image..."
# 开始构建镜像(注意dockerfile 要在codeRootDir目录下)
docker build -t "${dockerImageName}:latest" "${codeRootDir}"
echo "Docker image built successfully."
#压缩保存镜像到codeRootDir目录下
echo "Saving Docker image to file..."
docker save "${dockerImageName}:latest" | gzip > "${codeRootDir}/${dockerImageName}.tar.gz"
echo "Docker image saved successfully."
# 远程传输到目标服务器
echo "Uploading Docker image to server..."
scp -C "${codeRootDir}/${dockerImageName}.tar.gz" root@"${remoteHost}":"${remoteRootDir}/"
echo "Upload completed."
# 远程执行命令
echo "Deploying on remote server..."
ssh root@"${remoteHost}" "
cd ${remoteRootDir} &&
# 解压镜像,并加载镜像到本地
gunzip -c ${dockerImageName}.tar.gz | docker load &&
# 查询当前是否有该镜像服务运行,有则删除该镜像后从新运行镜像
docker ps -q --filter 'name=${containerName}' | grep -q . && docker rm -f ${containerName} || true &&
docker run -d --name ${containerName} --privileged=true --restart=always -p 8090:80 ${dockerImageName}:latest
"
echo "Deployment completed."
Vue项目代码对应改造
在项目package.json同级目录下创建 Dockerfile、nginx.conf、nginx.default.config 文件
package.json
定义的install 、 bulid 、run命令
"scripts": {
"serve": "vue-cli-service serve",
"build": "vue-cli-service build",
"build:report": "vue-cli-service build --report",
"globle": "npm install -g cnpm --registry=https://registry.npm.taobao.org&&cnpm i rimraf npm-check-updates nrm -g&&rimraf node_modules&&cnpm i",
"lint": "eslint --fix --ext .js,.vue src",
"lint:style": "stylelint-config-prettier-check",
"inspect": "vue-cli-service inspect",
"template": "plop",
"clear": "rimraf node_modules&&npm install --registry=https://registry.npm.taobao.org",
"use:npm": "nrm use npm",
"use:taobao": "nrm use taobao",
"update": "ncu -u --reject sass-loader,sass,screenfull,eslint&&cnpm i",
"update:globle": "ncu -g --concurrency 10 --timeout 80000",
"push": "start ./push.sh",
"deploy": "start ./deploy.sh"
},
Dockerfile
FROM nginx
MAINTAINER vue-admin-beautiful
LABEL description=本项目基于vue-admin-beautiful开源版构建
LABEL qq=783963206
# 环境变量
ENV TZ=Asia/Shanghai \
RUN_USER=nginx \
RUN_GROUP=nginx \
DATA_DIR=/data/web \
LOG_DIR=/data/log/nginx
# 工作目录
WORKDIR ${DATA_DIR}
# 日志输出
RUN ["echo","vue-admin-beautiful - UI building..."]
# 切换为上海时区
RUN ln -sf /usr/share/zoneinfo/$TZ /etc/localtime \
&& echo $TZ > /etc/timezone
# 创建日志文件夹
RUN mkdir ${LOG_DIR} -p
RUN chown nginx.nginx -R ${LOG_DIR}
# 拷贝dist包文件
COPY ./dist ./
# 拷贝nginx配置文件
ADD nginx.conf /etc/nginx/nginx.conf
ADD nginx.default.conf /etc/nginx/conf.d/default.conf
EXPOSE 80
ENTRYPOINT nginx -g "daemon off;"
nginx.conf
user nginx;
worker_processes auto;
pid /var/run/nginx.pid;
events {
use epoll;
worker_connections 51200;
multi_accept on;
}
http {
include /etc/nginx/mime.types;
default_type application/octet-stream;
server_names_hash_bucket_size 512;
client_header_buffer_size 32k;
large_client_header_buffers 4 32k;
client_max_body_size 50m;
log_format main '$remote_addr - $remote_user [$time_local] "$request" '
'$status $body_bytes_sent "$http_referer" '
'"$http_user_agent" "$http_x_forwarded_for"';
access_log /var/log/nginx/access.log main;
sendfile on;
tcp_nopush on;
tcp_nodelay on;
keepalive_timeout 65;
# gzip 压缩
gzip on;
gzip_min_length 1k;
gzip_buffers 4 16k;
gzip_http_version 1.1;
gzip_comp_level 2;
gzip_types text/plain application/javascript application/x-javascript text/javascript text/css application/xml;
gzip_vary on;
gzip_proxied expired no-cache no-store private auth;
gzip_disable "MSIE [1-6]\.";
limit_conn_zone $binary_remote_addr zone=perip:10m;
limit_conn_zone $server_name zone=perserver:10m;
include /etc/nginx/conf.d/*.conf;
}
nginx.default.conf
server {
listen 80;
server_name localhost;
access_log /data/log/nginx/access.log main;
error_log /data/log/nginx/error.log;
# 静态资源
location / {
root /data/web;
index index.html index.htm;
try_files $uri $uri/ /index.html;
}
# 前端代理(注意这里需要填写 真实后端ip)
location /api/ {
//注意 http:ip:8090/ 和http:ip:8090的区别
// http:ip:8090/会去掉/api这一层
// http:ip:8090 不会去掉/api这一层
proxy_pass http://~~真实后端ip:8090~~ ;
add_header Access-Control-Allow-Origin *;
add_header Access-Control-Allow-Credentials: true;
add_header Access-Control-Allow-Methods GET,POST,OPTIONS,PUT,DELETE;
proxy_http_version 1.1;
# 连接延时
proxy_connect_timeout 3600s;
proxy_read_timeout 3600s;
proxy_send_timeout 3600s;
# IP 穿透
proxy_set_header Host $proxy_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
# WebSocket 穿透
proxy_set_header Origin "";
proxy_set_header Upgrade $http_upgrade;
proxy_set_header Connection "upgrade";
}
网络请求路径
部署前端项目地址
remoteHost=“10.30.222.11”
// 服务的地址+8090 根据nginx配置对应转发到真实的ip中
vue项目默认请求前缀
http://10.30.222.11:8090/api
构建部署
部署成功日志
访问路径
10.30.222.11:8090