本文最后更新于 804 天前,其中的信息可能已经有所发展或是发生改变。
背景
项目里存放了部署到测试环境的k8s资源定义文件,这部分文件需要提交到一个资源定义文件集中仓库,给运维部署到生产环境用。但这部分文件可能会改动,例如存放的项目配置文件就是以configmap的形式在k8s中使用,如果更改项目配置,就需要同步提交到集中仓库。
最开始,这部分工作是人工手动完成的,但是一份文件保存在多个地方,就可能出现不同步的问题,导致每次部署新环境,经常出现因资源定义文件不是最新版而出现应用异常。
这种重复性工作完全可以通过程序来实现自动化操作,这里通过 Gitlab CI 流水线来解决。
公共仓库脚本
公共脚本仓库具体看Gitlab CI/CD 实践七:公共脚本仓库,实际使用请看Gitlab CI/CD 实践四:Golang 项目 CI/CD 流水线配置
common/sync-deploy-file-to-template/.gitlab-ci.yml
.sync_deploy_file_to_template: &sync_deploy_file_to_template
echo "-------------------- 同步部署文件到 template 仓库,用于生产环境部署 --------------------";
echo "-------------------- 配置 git ssh,实现免密提交到 ${TARGET_REPOSITORY} 仓库 --------------------";
eval $(ssh-agent -s)
ssh-add <(echo "$CI_AUTO_SYNC_SSH_PRIVATE_KEY");
mkdir -p ~/.ssh;
touch ~/.ssh/config;
echo "StrictHostKeyChecking no" >> ~/.ssh/config;
echo "UserKnownHostsFile /dev/null" >> ~/.ssh/config;
echo "-------------------- 配置 git 用户信息为当前触发流水线的用户 --------------------";
git config --global user.email "$GITLAB_USER_EMAIL";
git config --global user.name "$GITLAB_USER_LOGIN";
echo "-------------------- git clone ${TARGET_REPOSITORY} 仓库,只拉取指定分支的最后一次 commit --------------------";
cd /tmp;
git clone --depth 1 --branch $TARGET_BRANCH $TARGET_REPOSITORY_ADDR;
echo "-------------------- 找出全部部署文件 --------------------";
cd $CI_PROJECT_DIR;
FILES=$(find ${SOURCE_DIR} -name "*.yaml") && echo $FILES;
echo "-------------------- 拷贝 test 环境的部署文件到 ${TARGET_REPOSITORY} 仓库--------------------";
for FILE in $FILES; do
DIR=$(dirname "$FILE");
cd $DIR;
ENV=${DIR##*/};
if [ "$ENV" = "test" ]; then
SUB_MODULE=${DIR%/*};
SUB_MODULE=${SUB_MODULE##*/};
CURR_FILE=${FILE##*/};
sed -i "s/IMAGE_VERSION/latest/g" $CURR_FILE;
sed -i "s/NAME_SPACE/${NAME_SPACE}/g" $CURR_FILE;
sed -i "s/IMAGE_NAME/${MODULE_PREFIX}-${SUB_MODULE}/g" $CURR_FILE;
sed -i "s/DOCKER_REGISTRY_ADDR/${DOCKER_REGISTRY_ADDR}/g" $CURR_FILE;
sed -i "s/IMAGE_GROUP/${IMAGE_GROUP}/g" $CURR_FILE;
TARGET_FILE_NAME=${MODULE_PREFIX}-${SUB_MODULE}-$CURR_FILE;
echo "TARGET_FILE_NAME $TARGET_FILE_NAME";
cp -r $CURR_FILE /tmp/${TARGET_REPOSITORY}/${TARGET_DIR}/${TARGET_FILE_NAME};
fi;
cd - > /dev/null;
done;
echo "-------------------- 提交到 ${TARGET_REPOSITORY} 仓库 --------------------";
cd /tmp/$TARGET_REPOSITORY;
git add .;
git commit -m "sync: 通过 ${CI_PROJECT_PATH} gitlab ci 自动同步部署文件" || true;
git pull;
git push;
echo "-------------------- 同步成功 --------------------";
.sync_deploy_file_to_template_base:
stage: sync
image:
name: 172.1.1.1/common/ubuntu:20.04
tags:
- 172.1.1.2-runner
interruptible: true
variables:
MODULE_PREFIX: default
IMAGE_GROUP: default
NAME_SPACE: default
# 同步目标仓库信息
TARGET_REPOSITORY: template
# 待同步的deployment文件夹
SOURCE_DIR: ./deploy
# 必须是ssh地址,因为需要使用ssh免密登录
TARGET_REPOSITORY_ADDR: git@git.google.com:ads/template.git
TARGET_BRANCH: main
TARGET_DIR: default
script:
- *sync_deploy_file_to_template
项目里如何使用
-
增加 sync 阶段
stages: - sync
-
引入此
yml
include: - project: 'devops/gitlab-cicd-template' ref: main file: '/common/sync-deploy-file-to-template/.gitlab-ci.yml'
-
配置全局变量,每个项目只配置一个
variables
variables: &global-variables # 用于拼接镜像名 MODULE_PREFIX: google-ads # 镜像私仓里的项目 IMAGE_GROUP: ads # 拷贝部署文件到template仓库的目录 TARGET_DIR: ads
-
新增一个job
sync_deploy_file_to_template: extends: - .sync_deploy_file_to_template_base variables: <<: *global-variables NAME_SPACE: ads
- 这里的
NAME_SPACE
用于替换部署文件里的NAME_SPACE
变量
- 这里的
厉害,太赞了