基于Jenkins和GitLab的前端自动化实践

907 阅读5分钟

概述

什么是前端自动化

前端自动化是指前端代码的自动化构建、打包、测试及部署等一系列流程

为什么要做前端自动化

  • 减少开发人员重复工作,也能降低人为工作的失误
  • 效率迭代,便捷部署
  • 快速交付,便于管理

整体流程

image.png

说明:

  1. 当GitLab生成新的标签时,Jenkins会自动触发构建任务,以最新生成的标签版本构建一个Docker 镜像,并且启动该镜像,将最新的前端资源进行打包部署
  2. 也支持在Jenkins上选择tag版本,手动构建任务,这样便于版本回退和管理

实现步骤

一、GitLab私有化部署

内容较多,单独整理成GitLab私有化部署

二、Jenkins私有化部署

内容较多,单独整理成Jenkins私有化部署

三、GitLab触发Jenkins自构建

其核心是基于GitLab的webhook机制,webhook的详细解释推荐这篇文章。个人理解:webhook 是一种基于 HTTP 的回调函数,它是两个应用之间的发布与订阅

在这个场景下,GitLab是服务端,Jenkins是客户端。GitLab接收到自己页面发送的“标签推送事件”后发布了该消息,Jenkins可以通过webhook接收到该消息并做处理。如果不使用webhook,Jenkins也可以使用轮询的方式

以下为具体配置步骤:

1. 安装GitLab 插件

2. 配置触发时机

  1. 选择“Build when a change is pushed to GitLab”
  2. 点击Generate 生成一个Secret token

image.png

image.png

3. 配置GitLab webhooks

  1. 填写url,这个url就在Jenkins “Build when a change is pushed to GitLab” 后面
  2. 填写Jenkins刚刚生成的secret token
  3. 触发来源勾选“标签推送事件”
  4. SSL 验证取决于你的Jenkins服务是http还是https,如果是http就取消勾选

image.png

image.png

4. 测试webhooks

点击 “标签推送事件”,Jenkins自动触发一次构建,则配置成功

image.png

image.png

四、前端项目Dockerfile配置

Docker通过读取Dockerfile的指令自动构建镜像。所以在项目中加入Dockerfile文件的目的,就是为了能够将项目整体构建为一个Docker镜像。然后再使用Docker命令,以此镜像创建容器服务。

Dockerfile的完整语法和最佳实践。可以参考官方文档

以下为配置Dockerfile的示例步骤

1. .dockerignore文件配置

项目根目录下创建 .dockerignore 。作用是复制项目时忽略某些文件。根据需要填写,类似.gitignore。示例:

# dependencies
node_modules

# production
build
dist

# misc
.DS_Store
*.swp
*.dia~

# logs
*.log

# local env files
.env*.local

# tmp
.ice
.faas_debug_tmp
.severless

# Runtime data
.idea
.vscode

2. Dockerfile文件配置

项目根目录下创建Dockerfile文件

# build stage

FROM node:18 as build-stage

# 创建一个工作目录
WORKDIR /app

# 将当前目录下的所有内容拷贝到工作目录
COPY . /app

# 安装依赖
RUN npm install --registry=https://registry.npmmirror.com

# 打包
RUN npm run build


# production stage

FROM nginx:stable-alpine as production-stage

# 将刚刚打好包的dist目录复制到nginx目录下
COPY --from=build-stage /app/dist /usr/share/nginx/html

# 暴露的端口
EXPOSE 80

# 指定在容器中运行的命令
CMD ["nginx", "-g", "daemon off;"]

3. 本地测试:构建镜像

执行 docker build -t react-nginx:1.0.0 . 命令

  1. “-t”代表tag,后面指定镜像文件的名称。名称后面可以指定版本,如果不指定则是latest\
  2. 名称后面紧跟“:”可以指定版本,如果不指定则是latest
  3. “.”表示Dockerfile文件所在路径

如果构建成功,使用docker images 命令查看,就可以看到刚刚构建的镜像。以及一些基础信息。

image.png

4. 本地测试:生成容器

执行 docker run -d -p 80:80 --name react-nginx react-nginx:1.0.0

如果运行成功,通过docker ps命令查看容器

image.png

至此,在本机访问localhost,应该能正常展示前端项目的页面了。之所以在本地测试创建镜像和生成容器的步骤。是因为本地排查、调试和修改比较方便

五、Jenkins构建任务配置

前面的步骤,都是为了这一步做准备。最后一步就是将前文内容串联起来。达到自动化打包部署的目的。

1. 新建Jenkins任务

新建Jenkins任务以及配置GitLab代码拉取。这一部分在Jenkins私有化部署中有详细说明,这里不在赘述

2. 参数化构建配置

  1. 安装 “Build With Params” 插件和 “Persistent Parameter” 插件:添加自定义参数
  2. 安装“Git Paramet” 插件:使用Git相关参数。如tag、branch等
  3. 选择“参数化构建过程” => 选择“Git参数”
  4. 填写变量名,选择参数类型为“标签”,填写默认值

image.png

image.png

3. 指定构建分支

默认是mater,将其指定为上面定义的标签变量,示例中就是${tag}

image.png

4. 配置Build Steps

特别注意,这里在shell脚本中直接使用docker命令,它本质上是使用了宿主机上的docker而非容器内部。能够这样使用的关键是启动容器时加上 --privileged=true。这个在Jenkins私有化部署中也有说明。

  1. 找到Build Steps,点击“增加构建步骤” => 点击“执行shell”

image.png

  1. 编写shell执行脚本
    构建镜像和启动容器的过程同本地测试是一样的。增加了容器是否正在运行的判断。如果正在运行则先停止并删除容器,再启动。
echo "tag版本:${tag}"
# 构建 react-nginx 镜像。${tag:1}语法报错?
docker build -t react-nginx:${tag#*v} .

# 获取当前docker运行的 react-nginx 容器id
containerId=$(docker ps -a -q -f "name=react-nginx");


# 判断 containerId 是否存在
if [ -n $containerId ]
then
    # react-nginx 容器已经运行,则需要先停止,并删除
	 echo "${containerId} 正在运行"
    docker stop ${containerId}
    docker rm ${containerId}
fi

docker run  -d -p 80:80 --name react-nginx react-nginx:${tag#*v}

效果测试

方式一:GitLab新建标签,成功后Jenkins自动以新建的这个标签版本构建docker镜像并运行

image.png

方式二:手动构建,选择tag版本

image.png

遗留问题

因本人知识有限,实践过程中遇到了部分问题没有解决或者不甚明白。如果有大佬知晓其中原因,还请评论告知,多谢。

  1. Jenkins私有化部署后,拉取GitLab代码时权限有问题。即使在GitLab部署了密钥,Jenkins中也新增了全局凭证。依然需要在Jenkins容器内拉取一次Git 仓库代码,手动确认连接。
  2. Jenkins中的shell有些语法会报错。比如上文中截取字符串使用${tag:1}就直接报错了,而在本地使用.sh文件调试时是正常的。
  3. 新增版本后就会构建一个新版本的镜像留在云服务器上,长此以往,云服务器空间会被沾满。这一点可以在shell脚本执行构建时先清除之前的镜像。这里本人先定时手动清除,后续补充。