侧边栏壁纸
博主头像
SeaDream乄造梦

Dream,Don't stop a day of hard and don't give up a little hope。 ——不停止一日努力&&不放弃一点希望。

  • 累计撰写 56 篇文章
  • 累计创建 21 个标签
  • 累计收到 14 条评论

目 录CONTENT

文章目录

docker 部署jenkins,集成go&&前端自动化部署

SeaDream乄造梦
2024-11-25 / 0 评论 / 0 点赞 / 68 阅读 / 16,774 字
温馨提示:
亲爱的,如果觉得博主很有趣就留下你的足迹,并收藏下链接在走叭

docker部署jenkins并且实现go程序和前端程序自动化部署,看这一篇就够了。
这篇博文记录了我从零到一部署jenkins时踩的坑,并一步一步解决的过程。

jenkins部署失败方案

容器部署

拉取最新jenkins镜像,并部署容器

docker run --name jenkins -u root  -d -p 8086:8080 -p 50000:50000 \
-e JAVA_OPTS="-Dorg.apache.commons.jelly.tags.fmt.timeZone='Asia/Shanghai" \
--restart=always \
-v /xxx/jenkins/jenkins_home:/var/jenkins_home \
-v /xxx/jenkins/docker.sock:/var/run/docker.sock \
-v /usr/bin/docker:/usr/bin/docker \ 
jenkinsci/blueocean

初始化

浏览器访问: ip+端口
发现安装插件报错
进一步排查,发现版本过低,不支持安装这些插件。
然后升级版本。
升级完版本后发现,最新版本java8 不能运行。于是开始升级java环境。

使用dockerfile部署,指定镜像java版本

# 使用官方 Jenkins 镜像作为基础镜像
FROM jenkins/jenkins:latest

# 设置环境变量,指定时区
ENV TZ=Asia/Shanghai

# 使用 apt-get 更新包列表并安装 Java 17
USER root
RUN apt-get update && \
    apt-get install -y openjdk-17-jdk && \
    rm -rf /var/lib/apt/lists/*

# 设置 JAVA_HOME 环境变量
ENV JAVA_HOME=/usr/lib/jvm/java-17-openjdk-amd64

# 更改权限,确保 Jenkins 用户可以执行 docker 命令
RUN chmod +x /usr/bin/docker

# 将 jenkins 用户添加到 docker 组,以便在容器内运行 docker 命令
RUN usermod -aG docker jenkins

# 清理工作
USER jenkins

进入该dockerfile文件目录下运行下面命令构建镜像

docker build -t my-jenkins .

注意,java11下载依赖下载得需要些时间
image.png
待镜像构建成功后,从此镜像启动容器

docker run --name jenkins -u root -d -p 8086:8080 -p 50000:50000 \
-e JAVA_OPTS="-Dorg.apache.commons.jelly.tags.fmt.timeZone='Asia/Shanghai'" \
--restart=always \
-v /xxx/jenkins_new/jenkins_home:/var/jenkins_home \
-v /xxx/jenkins_new/docker.sock:/var/run/docker.sock \
-v /xxx/jenkins_new/bin/docker:/usr/bin/docker \
my-jenkins

网络问题,失败构建。寻求其他方案

jenkins部署成功方案

最后发现,只有jenkins最新版本安装插件时才不会有大量报错

备注

我使用的是docker-compose部署的go程序,所以需要在宿主机上安装docker-compose,docker,go环境。相关环境安装移步后面标题。

  1. 拉取镜像
docker pull jenkins/jenkins:2.456
  1. 运行容器
docker run --name jenkins -u root  -d -p 8086:8080 -p 50000:50000   -e JAVA_OPTS="-Dorg.apache.commons.jelly.tags.fmt.timeZone='Asia/Shanghai"  --restart=always  -v /xxx/jenkins_new/jenkins_home:/var/jenkins_home  -v /var/run/docker.sock:/var/run/docker.sock  -v  /usr/bin/docker:/usr/bin/docker   -v /usr/local/go:/usr/local/go    -v /usr/local/bin/docker-compose:/usr/local/bin/docker-compose     jenkins/jenkins:2.456
  1. 查看初始密码
cat /xxx/jenkins_new/jenkins_home/secrets/initialAdminPassword
  1. 安装推荐插件
    image.png

初始化

汉化

初始化管理员账号密码邮箱等信息
进来后你会发现不是完全汉化版本,删除默认汉化插件,重新安装并重启容器。
进入插件管理搜索 “locale”
image.png
重启容器后
image.png

其他必要插件

安装 Publish over SSH、docker-build-step 、Docker Commons 插件

image.png

image.png

配置服务器信息

image.png
image.png
测试连通性
image.png

构建项目

image.png
image.png

宿主机安装go环境并代理到jenkins容器

运行发现报错找不到go命令,原因是jenkins容器中并没有go环境,因此需要安装go环境。两种方式:1.容器内安装go环境;2.宿主机安装go环境,挂载到容器

下面我们使用方式二:

宿主机中操作:

# 下载Go语言1.22.5二进制包
wget https://go.dev/dl/go1.22.5.linux-amd64.tar.gz
 
# 解压缩到/usr/local目录(这个目录是Go官方推荐的安装目录)
sudo tar -C /usr/local -xzf go1.22.5.linux-amd64.tar.gz
 
# 设置用户环境变量
echo 'export PATH=$PATH:/usr/local/go/bin' >> ~/.profile
echo 'export GOPATH=$HOME/go' >> ~/.profile
source ~/.profile

# 设置系统环境变量
echo 'export PATH=$PATH:/usr/local/go/bin' >> /etc/profile
echo 'export GOPATH=$HOME/go' >> /etc/profile
source /etc/profile

# 检查是否安装成功
go version

go env -w GO111MODULE=on
go env -w GOPROXY=https://goproxy.cn,direct
//删除容器,并挂载配置文件路径后重新启动
docker stop jenkins
docker rm jenkins
//重新启动
docker run --name jenkins -u root  -d -p 8086:8080 -p 50000:50000   -e JAVA_OPTS="-Dorg.apache.commons.jelly.tags.fmt.timeZone='Asia/Shanghai"  --restart=always  -v /xxx/jenkins_new/jenkins_home:/var/jenkins_home  -v /var/run/docker.sock:/var/run/docker.sock  -v  /usr/bin/docker:/usr/bin/docker   -v /usr/local/go:/usr/local/go    -v /usr/local/bin/docker-compose:/usr/local/bin/docker-compose     jenkins/jenkins:2.456

安装docker-compose

为什么不效仿go环境一样:宿主机安装环境,挂载到jenkins容器呢?
应为docker-compose启动是通过python,如果宿主机安装代理后,还需要为jenkins容器安装python环境

直接在jenkins容器中直接安装docker-compose

  1. 开始
docker exec -it jenkins bash

curl -L "https://github.com/docker/compose/releases/download/1.29.2/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
chmod +x /usr/local/bin/docker-compose
docker-compose --version
  1. 输出信息:
root@9f4de87d743f:/# curl -L "https://github.com/docker/compose/releases/download/1.29.2/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
  0     0    0     0    0     0      0      0 --:--:-- --:--:-- --:--:--     0
  0 12.1M    0 70992    0     0  34265      0  0:06:11  0:00:02  0:06:09 62603
  3 12.1M    3  458k    0     0   2142      0  1:39:06  0:03:39  1:35:27  4134
curl: (92) HTTP/2 stream 1 was not closed cleanly: PROTOCOL_ERROR (err 1)
root@9f4de87d743f:/# chmod +x /usr/local/bin/docker-compose
root@9f4de87d743f:/# docker-compose --version
[183] Cannot open self /usr/local/bin/docker-compose or archive /usr/local/bin/docker-compose.pkg
  1. 分析:
    在 Jenkins 容器中通过 curl 下载 docker-compose 文件时出现了问题,导致文件不完整(Cannot open self 错误通常是因为文件损坏或下载未完成)。

在宿主机中下载docker-compose挂载到jenkins容器中

1.下载

curl -L "https://github.com/docker/compose/releases/download/1.29.2/docker-compose-$(uname -s)-$(uname -m)" -o docker-compose
chmod +x docker-compose
  1. 确认文件大小和权限是否正确:
ls -lh docker-compose
  1. 挂载到容器中:
docker run --name jenkins -u root  -d -p 8086:8080 -p 50000:50000   -e JAVA_OPTS="-Dorg.apache.commons.jelly.tags.fmt.timeZone='Asia/Shanghai"  --restart=always  -v /xxx/jenkins_new/jenkins_home:/var/jenkins_home  -v /var/run/docker.sock:/var/run/docker.sock  -v  /usr/bin/docker:/usr/bin/docker   -v /usr/local/go:/usr/local/go    -v /usr/local/bin/docker-compose:/usr/local/bin/docker-compose     jenkins/jenkins:2.456
  1. 在容器中确认是否正确安装:
docker exec -it jenkins bash
docker-compose --version

编写构建shell脚本

image.png

#!/bin/bash

##### 环境变量 #####
env="test"
project_name="zhijian"
name="zhi-client"
time=$(date "+%Y%m%d%H%M%S")
image="${project_name}/${name}:${time}"


##### 打印脚本执行开始时间 #####
echo "脚本开始执行,时间:$(date "+%Y-%m-%d %H:%M:%S")"
echo "当前工作目录:$(pwd)"

##### 设置 Go 环境 #####
export GOROOT=/usr/local/go
export PATH=$PATH:$GOROOT/bin
export GOPROXY=https://goproxy.cn

##### 检查 Go 是否安装 #####
if ! command -v go &>/dev/null; then
    echo "错误: Go 未安装,请先安装 Go 环境!"
    exit 1
fi

##### 清理 Go 模块缓存并下载依赖 #####
echo "正在清理 Go 模块缓存并下载依赖..."
go mod tidy
if [ $? -ne 0 ]; then
    echo "错误: Go 模块下载失败,请检查依赖!"
    exit 1
fi

echo "进入$env环境"
cd env/$env
echo "当前工作目录:$(pwd)"
ls

##### 编译 Go 程序 #####
echo "正在删除旧的 main 文件..."
rm -rf ./main
if [ $? -ne 0 ]; then
    echo "警告: 删除旧的 main 文件失败,可能不存在。"
fi
ls


echo "正在编译 Go 程序..."
go build ../../main.go
if [ $? -ne 0 ]; then
    echo "错误: Go 程序编译失败,请检查代码!"
    exit 1
fi
echo "Go 程序编译完成!"
ls

##### 构建 Docker 镜像 #####
echo "正在构建 Docker 镜像,名称为:$image"
docker build -t $image .
if [ $? -ne 0 ]; then
    echo "错误: Docker 镜像构建失败,请检查 Dockerfile!"
    exit 1
fi

##### 检查 docker-compose 是否安装 #####
if ! command -v docker-compose &>/dev/null; then
    echo "错误: docker-compose 未安装,请先安装 docker-compose!"
    exit 1
fi

##### 停止并移除所有容器 #####
echo "正在停止所有容器..."
docker-compose down
if [ $? -ne 0 ]; then
    echo "错误: 容器停止失败,请检查 docker-compose 配置!"
    exit 1
fi

##### 构建并启动容器 #####
echo "正在构建并启动容器..."
DOCKER_IMAGE=$image docker-compose up -d
if [ $? -ne 0 ]; then
    echo "错误: 容器启动失败,请检查 docker-compose 配置!"
    exit 1
fi

# 获取镜像的完整标识(按时间排序,保留最新的 3 个,删除其余的)
echo "清理旧镜像,保留最新 3 个..."
docker images --filter=reference="*/$name:*" --format "{{.Repository}}:{{.Tag}} {{.CreatedAt}}" \
    | sort -rk 2 | tail -n +4 | awk '{print $1}' | xargs -r docker rmi -f

echo "旧镜像清理完成!"

##### 打印容器状态 #####
echo "正在获取容器状态..."
docker-compose ps

##### 打印脚本执行结束时间 #####
echo "脚本执行完成,时间:$(date "+%Y-%m-%d %H:%M:%S")"

清理镜像逻辑

docker images --filter=reference="*/$name:*" --format "{{.Repository}}:{{.Tag}} {{.CreatedAt}}" \
    | sort -rk 2 | tail -n +4 | awk '{print $1}' | xargs -r docker rmi -f

  1. 筛选特定镜像:
docker images --filter=reference="*/$name:*" --format "{{.Repository}}:{{.Tag}} {{.CreatedAt}}"

  • filter=reference="/$name:":筛选所有与 zhi-client 名称匹配的镜像。
  • format "{}:{} {}":输出格式为 REPOSITORY:TAG CreatedAt。
  1. 按时间排序:
  • 按 CreatedAt 降序排列,最新的镜像排在最前。
  1. 跳过最新的 3 个:
tail -n +4
  • 跳过前三行(保留最近三个镜像)。
  1. 提取镜像名称:
awk '{print $1}'
  • 提取 REPOSITORY:TAG,作为删除镜像的输入。
  1. 删除多余镜像:
xargs -r docker rmi -f
  • 批量删除镜像,-r 确保在没有多余镜像时不执行删除命令。

这里由于是docker-compose 部署的,所以出现共用同一网桥问题。换docker直接部署

#!/bin/bash

##### 环境变量 #####
env="test"
project_name="xxx"
name="xxx"
time=$(date "+%Y%m%d%H%M%S")
image="${project_name}/${name}:${time}"
container_name="xxx"

##### 打印脚本执行开始时间 #####
echo "脚本开始执行,时间:$(date "+%Y-%m-%d %H:%M:%S")"
echo "当前工作目录:$(pwd)"

##### 设置 Go 环境 #####
export GOROOT=/usr/local/go
export PATH=$PATH:$GOROOT/bin
export GOPROXY=https://goproxy.cn

##### 检查 Go 是否安装 #####
if ! command -v go &>/dev/null; then
    echo "错误: Go 未安装,请先安装 Go 环境!"
    exit 1
fi

##### 清理 Go 模块缓存并下载依赖 #####
echo "正在清理 Go 模块缓存并下载依赖..."
go mod tidy
if [ $? -ne 0 ]; then
    echo "错误: Go 模块下载失败,请检查依赖!"
    exit 1
fi

##### 进入指定环境目录 #####
echo "进入 $env 环境"
cd "env/$env" || { echo "错误: 无法进入目录 env/$env"; exit 1; }
echo "当前工作目录:$(pwd)"
ls

##### 编译 Go 程序 #####
echo "正在删除旧的 main 文件..."
rm -rf ./main
if [ $? -ne 0 ]; then
    echo "警告: 删除旧的 main 文件失败,可能不存在。"
fi

echo "正在编译 Go 程序..."
go build ../../main.go
if [ $? -ne 0 ]; then
    echo "错误: Go 程序编译失败,请检查代码!"
    exit 1
fi
echo "Go 程序编译完成!"


##### 构建 Docker 镜像 #####
echo "正在构建 Docker 镜像,名称为:$image"
docker build -t "$image" .
if [ $? -ne 0 ]; then
    echo "错误: Docker 镜像构建失败,请检查 Dockerfile!"
    exit 1
fi

##### 停止并删除现有容器 #####
echo "正在停止现有容器:$container_name"
if docker ps -q --filter "name=^/${container_name}$" | grep -q .; then
    docker stop "$container_name"
fi

echo "正在删除现有容器:$container_name"
if docker ps -a -q --filter "name=^/${container_name}$" | grep -q .; then
    docker rm "$container_name"
fi

##### 启动新容器 #####
echo "正在启动新容器:$container_name"
docker run -d \
    --name "$container_name" \
    --restart always \
    -p 7788:7788 \
    -e TZ="Asia/Shanghai" \
    -v /usr/share:/usr/share \
    -v /xxx/xxx/xxx-mini/log:/xxx/xxx/log \
    -v /xxx/xxx/xxx-mini/cert:/xxx/xxx/cert \
    "$image"
if [ $? -ne 0 ]; then
    echo "错误: 容器启动失败,请检查日志!"
    exit 1
fi

##### 删除多余的旧镜像标签 #####
echo "清理旧镜像标签,保留最近 3 个..."

# 获取目标镜像的所有标签,按创建时间排序,排除最近 3 个
docker images --format "{{.Repository}}:{{.Tag}} {{.CreatedAt}}" | \
grep "$name" | \
sort -k2,2 -r | \
tail -n +4 | \
awk '{print $1}' | \
xargs -r docker rmi -f

if [ $? -eq 0 ]; then
    echo "旧镜像标签清理完成!"
else
    echo "警告: 旧镜像清理过程中出现问题,请手动检查。"
fi

##### 打印容器状态 #####
echo "正在获取容器状态..."
docker ps -a | grep $container_name

##### 打印脚本执行结束时间 #####
echo "脚本执行完成,时间:$(date "+%Y-%m-%d %H:%M:%S")"


最后

讨论

  1. 过程中是不是会觉得不断删除容器,在创建容器,那我之前的配置和初始化岂不是没了?
    非也,我们已经将容器数据挂载到了宿主机中,所以即使删除了容器,再次因为挂载地址问题重新创建容器,我们的数据并不会丢失。
  2. 这个过程是否太过麻烦?
    是的,使用docker部署jenkins确实麻烦。不仅需要考虑到环境的挂载,还需要寻找docker中jenkins最新版本。可以直接在官网下载jenkins的linux包,安装到宿主机上,这样就不用考虑环境挂载问题了。

参数解释:

docker run:
用来创建并启动一个容器。

--name jenkins:
给容器指定一个名称,容器的名字是 jenkins,以后可以通过这个名称来引用容器。

-u root:
以 root 用户身份运行容器。这通常是为了确保容器内有足够的权限来执行某些操作,如安装软件或执行 Docker 命令。

-d:
让容器以后台模式运行。即容器在启动后会在后台运行,不会阻塞终端。

-p 8086:8080:
将宿主机的 8086 端口映射到容器的 8080 端口。Jenkins 的 Web UI 默认是通过 8080 端口访问的,容器内的 8080 端口会映射到宿主机的 8086 端口,允许从宿主机访问 Jenkins。

-p 50000:50000:
将宿主机的 50000 端口映射到容器的 50000 端口。这个端口用于 Jenkins 的代理连接。代理通常使用该端口来连接主 Jenkins 实例。

-e JAVA_OPTS="-Dorg.apache.commons.jelly.tags.fmt.timeZone='Asia/Shanghai'":
设置一个环境变量 JAVA_OPTS,并配置时区为 Asia/Shanghai,即设置容器内的时区为上海时间。

--restart=always:
设置容器自动重启策略。如果容器停止或崩溃,Docker 会自动重新启动容器。always 表示无论容器停止的原因如何,都将自动重启。

-v /xxx/jenkins_new/jenkins_home:/var/jenkins_home:
将宿主机路径 /xxx/jenkins_new/jenkins_home 挂载到容器内的 /var/jenkins_home 目录。这是 Jenkins 容器的默认工作目录,保存所有 Jenkins 的配置、插件和构建数据。挂载宿主机目录可以持久化 Jenkins 的数据。

-v /var/run/docker.sock:/var/run/docker.sock:
将宿主机的 Docker socket 文件 /var/run/docker.sock 挂载到容器内。这是为了让容器内的 Jenkins 能够与宿主机的 Docker 引擎进行通信,执行 Docker 命令(比如创建、启动容器)。

-v /usr/bin/docker:/usr/bin/docker:
将宿主机的 Docker 可执行文件 /usr/bin/docker 挂载到容器内,使得容器内可以执行 Docker 命令。

-v /usr/local/go:/usr/local/go:
将宿主机的 Go 语言安装目录 /usr/local/go 挂载到容器内的同一目录。这通常用于构建 Go 语言项目的环境。

-v /usr/local/bin/docker-compose:/usr/local/bin/docker-compose:
将宿主机的 docker-compose 可执行文件 /usr/local/bin/docker-compose 挂载到容器内。这使得容器内的 Jenkins 可以使用宿主机的 docker-compose 工具。

jenkins/jenkins:2.456:
这是指定要使用的 Docker 镜像,jenkins/jenkins 是官方的 Jenkins 镜像,版本号为 2.456。这个镜像包含了 Jenkins 的所有依赖和配置,能够在容器中运行 Jenkins。

前端部署

使用nvm安装node和npm

cd ~
curl -o- https://raw.githubusercontent.com/nvm-sh/nvm/v0.39.1/install.sh | bash


# 手动加载 nvm 的配置
export NVM_DIR="$HOME/.nvm"
[ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh"  # 这会加载 nvm
[ -s "$NVM_DIR/bash_completion" ] && \. "$NVM_DIR/bash_completion"  # 这会加载 bash_completion

nvm --version

nvm install 18
nvm use 18

node -v
npm -v

# 为了确保每次打开终端时都能自动加载 nvm 配置,可以将以下内容添加到 ~/.bashrc 文件中

export NVM_DIR="$HOME/.nvm"
[ -s "$NVM_DIR/nvm.sh" ] && \. "$NVM_DIR/nvm.sh"  # This loads nvm
[ -s "$NVM_DIR/bash_completion" ] && \. "$NVM_DIR/bash_completion"  # This loads nvm bash_completion

source ~/.bashrc

本地安装

wget https://nodejs.org/dist/v22.11.0/node-v22.11.0-linux-x64.tar.xz

mkdir /usr/local/lib/node

tar xf node-v22.11.0-linux-x64.tar.xz
mv node-v14.17.4-linux-x64 /usr/local/lib/node/nodejs


sudo vim /etc/profile

# 末尾加
export NODEJS_HOME=/usr/local/lib/node/nodejs
export PATH=$NODEJS_HOME/bin:$PATH

# 重新生效
source /etc/profile

node -v
npm -v

#配置淘宝镜像
# 显示当前源
npm config get registry
npm config set registry https://registry.npm.taobao.org
npm config get registry
# npm install -g cnpm --registry=https://registry.npm.taobao.org
npm --no-optional install -g cnpm --registry=https://registry.npm.taobao.org

【完结】

参考地址

jenkins本地部署

为什么要本地部署呢,本地部署不需要配置docker中的环境,大大缩短了配置时间

wget https://mirrors.tuna.tsinghua.edu.cn/jenkins/war/2.456/jenkins.war

java -jar jenkins.war --httpPort=8886

# 浏览器访问 ip+8886

# 查看密码
cat /root/.jenkins/secrets/initialAdminPassword

后台启动,并输出日志

nohup java -jar jenkins.war --httpPort=8080 > jenkins.log 2>&1 &

前端部署脚本

#!/bin/bash
export PATH=$PATH:/usr/local/lib/node/nodejs/bin
echo "检查node环境..."
node -v
npm -v

##### 环境变量 #####
env="dev"
project_name="dist"
time=$(date "+%Y%m%d%H%M%S")
build_dir="dist"
deploy_dir="/xxx/xxx/xxx/html/${project_name}" # Nginx 的静态文件目录

##### 打印脚本开始时间 #####
echo "脚本开始执行,时间:$(date "+%Y-%m-%d %H:%M:%S")"
echo "当前工作目录:$(pwd)"



##### 拉取最新代码 #####
echo "拉取最新代码..."
git pull origin $env
if [ $? -ne 0 ]; then
    echo "错误: 拉取代码失败,请检查 Git 仓库配置!"
    exit 1
fi

echo "当前工作目录:$(pwd)"

##### 安装依赖 #####
echo "安装依赖..."
cnpm i
if [ $? -ne 0 ]; then
    echo "错误: 依赖安装失败,请检查 package.json!"
    exit 1
fi

##### 构建项目 #####
echo "构建项目..."
cnpm run build
if [ $? -ne 0 ]; then
    echo "错误: 构建失败,请检查代码!"
    exit 1
fi

##### 部署静态文件 #####
echo "部署静态文件..."
rm -rf ${deploy_dir}
mkdir -p ${deploy_dir}
cp -r ${build_dir}/* ${deploy_dir}/
if [ $? -ne 0 ]; then
    echo "错误: 部署静态文件失败,请检查目录权限!"
    exit 1
fi

##### 打印部署结果 #####
echo "部署完成!静态文件已复制到:${deploy_dir}"
ls -lh ${deploy_dir}


##### 打印脚本结束时间 #####
echo "脚本执行完成,时间:$(date "+%Y-%m-%d %H:%M:%S")"

跨服务器部署

构建步骤1. 打包文件


##### 环境变量 #####
env="pro"
project_name="xxx_p"
name="xxx_p_name"
time=$(date "+%Y%m%d%H%M%S")
image="${project_name}/${name}:${time}"
container_name="xxx_p_name"


##### 打印脚本执行开始时间 #####
echo "脚本开始执行,时间:$(date "+%Y-%m-%d %H:%M:%S")"
echo "当前工作目录:$(pwd)"

##### 设置 Go 环境 #####
export GOROOT=/usr/local/go
export PATH=$PATH:$GOROOT/bin
export GOPROXY=https://goproxy.cn

##### 检查 Go 是否安装 #####
if ! command -v go &>/dev/null; then
    echo "错误: Go 未安装,请先安装 Go 环境!"
    exit 1
fi

##### 清理 Go 模块缓存并下载依赖 #####
echo "正在清理 Go 模块缓存并下载依赖..."
go mod tidy
if [ $? -ne 0 ]; then
    echo "错误: Go 模块下载失败,请检查依赖!"
    exit 1
fi

echo "进入$env环境"
cd env/$env
echo "当前工作目录:$(pwd)"
ls

##### 编译 Go 程序 #####
echo "正在删除旧的 main 文件..."
rm -rf ./main
if [ $? -ne 0 ]; then
    echo "警告: 删除旧的 main 文件失败,可能不存在。"
fi
ls


echo "当前工作目录:$(pwd)"
echo "正在编译 Go 程序..."

export GOPATH=/root/go
export GOROOT=/usr/local/go
export GOOS=linux
export GOARCH=amd64
export CGO_ENABLED=0

go build ../../main.go
if [ $? -ne 0 ]; then
    echo "错误: Go 程序编译失败,请检查代码!"
    exit 1
fi
echo "Go 程序编译完成!"
ls

步骤二,上传到其他服务器

image.png

ls
pwd

cd /xxx_p_name/xxx_p/xxx_p-web

ls

env="pro"
project_name="xxx_p"
name="zhi-client"
time=$(date "+%Y%m%d%H%M%S")
image="${project_name}/${name}:${time}"
container_name="zhi-client"

echo "当前工作目录:$(pwd)"

echo "当前目录下文件:$(ls)"

##### 构建 Docker 镜像 #####
echo "正在构建 Docker 镜像,名称为:$image"
docker build -t $image .
if [ $? -ne 0 ]; then
    echo "错误: Docker 镜像构建失败,请检查 Dockerfile!"
    exit 1
fi


##### 停止并删除现有容器 #####
echo "正在停止现有容器:$container_name"
if docker ps -q --filter "name=^/${container_name}$" | grep -q .; then
    docker stop "$container_name"
fi

echo "正在删除现有容器:$container_name"
if docker ps -a -q --filter "name=^/${container_name}$" | grep -q .; then
    docker rm "$container_name"
fi



##### 启动新容器 #####
echo "正在启动新容器:$container_name"
docker run -d \
    --name "$container_name" \
    --restart always \
    -p 8084:8084 \
    -e TZ="Asia/Shanghai" \
    -v /usr/share:/usr/share \
    -v /xxx_p_name/xxx_p/xxx_p-web/cert:/xxx_p_name/xxx_p/cert \
    "$image"
if [ $? -ne 0 ]; then
    echo "错误: 容器启动失败,请检查日志!"
    exit 1
fi


# 获取镜像的完整标识(按时间排序,保留最新的 3 个,删除其余的)
echo "清理旧镜像,保留最新 3 个..."
docker images --filter=reference="*/$name:*" --format "{{.Repository}}:{{.Tag}} {{.CreatedAt}}" \
    | sort -rk 2 | tail -n +4 | awk '{print $1}' | xargs -r docker rmi -f

echo "旧镜像清理完成!"

##### 打印容器状态 #####
echo "正在获取容器状态..."
docker ps -a | grep $container_name

##### 打印脚本执行结束时间 #####
echo "脚本执行完成,时间:$(date "+%Y-%m-%d %H:%M:%S")"


Jpom一键自动化部署

更轻量级的部署方案
jpom地址

goploy一键自动化部署

参考文档:

https://gitee.com/goploy/goploy#https://gitee.com/link?target=https%3A%2F%2Fhub.docker.com%2Fr%2Fzhenorzz%2Fgoploy

https://hub.docker.com/r/zhenorzz/goploy

https://docs.goploy.icu/#/dependency/rsync

0

评论区