从 GitLab 8.0 开始,GitLab CI 就已经集成在 GitLab 中,我们只要在项目中添加一个 .gitlab-ci.yml 文件,然后添加一个 Runner,即可进行持续集成。 而且随着 GitLab 的升级,GitLab CI 变得越来越强大,本文将介绍如何使用 GitLab CI 进行持续集成。
一些概念
在介绍 GitLab CI 之前,我们先看看一些持续集成相关的概念。
参考链接
https://segmentfault.com/a/1190000006120164
CI配置详解参考
https://segmentfault.com/a/1190000011881435
环境介绍:
develop分支: IP: 192.168.1.92 系统:centos7.4 web目录/develop/
test分支: IP: 192.168.1.136 系统:centos7.4 web目录/www/
master分支: IP: 192.168.1.61 系统:centos7.4 web目录/www/
gitlab服务器: IP: 192.168.1.37 系统:centos7.4
ssh端口都是22
gitlab服务器,需要安装gitlab,docker
docker的镜像列表如下:
kb-rsync
docker.io/gitlab/gitlab-runner
docker.io/alpine
其中kb-rsync是自己制作的,后续文章会讲到
192.168.1.92 需要安装dns服务器
.gitlab-ci.yml完整代码如下:
#镜像地址,通过docker images查看
image: kb-rsync
#构建阶段
stages:
#需要执行的流程,按照顺序来,就是deploy
- deploy
#定义环境变量
variables:
#项目名
PROJECT_NAME: kuaidihelp_monitor
#develop(开发分支),服务器IP地址
DEV_ADDRES_IP: "192.168.1.92"
#服务器ssh端口
DEV_ADDRES_PORT: "22"
#项目访问域名
DEV_DOMAIN: "http://${PROJECT_NAME}.baidu.com"
#test(测试分支)
TEST_ADDRES_IP: "192.168.1.136"
TEST_ADDRES_PORT: "22"
TEST_DOMAIN: "http://${PROJECT_NAME}.baidu.com"
#demo(预发布/灰度 分支)
#DEMO_ADDRES_IP: "10.20.1.179"
#DEMO_ADDRES_PORT: "2020"
#prod(线上master分支)
PROD_ADDRES_IP: "192.168.1.61"
PROD_ADDRES_PORT: "22"
PROD_DOMAIN: "http://${PROJECT_NAME}.baidu.com"
#gitlab服务器端口号
GITLAB_ADDRES_PORT: "22"
#gitlab访问地址
GITLAB_ADDRES_IP: "testgitlab.baidu.com"
#docker执行脚本前的动作
before_script:
#创建ssh目录
- mkdir -p ~/.ssh
#读取Settings->CI/CD->Secret variables 添加的公钥变量
- echo "$ID_RSA_PUB" > ~/.ssh/id_rsa.pub
#读取私钥变量,并设置权限为600(必须要600,否则报错)
- echo "$ID_RSA" > ~/.ssh/id_rsa && chmod 0600 ~/.ssh/id_rsa
#收集主机公钥,写入known_hosts,避免出现Are you sure you want to continue connecting (yes/no)?
#注意:ecdsa是针对centos7系统的,如果是centos6 需要使用rsa
#以下命令是将各个环境的主机公钥写入docker容器的~/.ssh/known_hosts文件
- ssh-keyscan -H -t ecdsa -p $DEV_ADDRES_PORT $DEV_ADDRES_IP >> ~/.ssh/known_hosts
- ssh-keyscan -H -t ecdsa -p $TEST_ADDRES_PORT $TEST_ADDRES_IP >> ~/.ssh/known_hosts
#因为目前还没有灰度环境,这里先注释掉
#- ssh-keyscan -H -t rsa -p $DEMO_ADDRES_PORT $DEMO_ADDRES_IP >> ~/.ssh/known_hosts
- ssh-keyscan -H -t ecdsa -p $PROD_ADDRES_PORT $PROD_ADDRES_IP >> ~/.ssh/known_hosts
- ssh-keyscan -H -t ecdsa -p $GITLAB_ADDRES_PORT $GITLAB_ADDRES_IP >> ~/.ssh/known_hosts
#deploy_dev(开发)任务
deploy_dev:
stage: deploy
script:
#将gitlab仓库代码同步到开发服务器,排除.git目录,代码以gitlab仓库为准,不匹配的,直接删除掉。
#将代码同步到测试服务器的/develop/目录下
- rsync -avztH -e "ssh -p $DEV_ADDRES_PORT" --exclude ".git" --delete ./ $DEV_ADDRES_IP:/develop/${PROJECT_NAME}/
only:
#当一个分支被push上来
- branches
tags:
#对应了注册runner的时候的tags
- dev
except:
#except是排除的意思,排除了master,test,除了develop以外的分支
- master
- test
- /^(?!develop).*$/
#environment 定义让job完成部署的环境名称
environment:
name: dev
url: $DEV_DOMAIN
#deploy_test(测试)任务
deploy_test:
stage: deploy
script:
#将代码同步到测试服务器的/www/目录下
- rsync -avztH -e "ssh -p $TEST_ADDRES_PORT" --exclude ".git" --delete ./ $TEST_ADDRES_IP:/www/${PROJECT_NAME}/
#只针对哪个分支
only:
#只针对于test分支
- test
tags:
#对应了注册runner的时候的tags
- vpc
environment:
name: test
url: $TEST_DOMAIN
#deploy_demo:
# stage: deploy
# script:
# - rsync -avztH -e "ssh -p $DEMO_ADDRES_PORT" --exclude ".git" --delete ./ $DEMO_ADDRES_IP:/www/${PROJECT_NAME}/
# when: manual
# only:
# - demo
# tags:
# - vpc
#deploy_prod(上线)任务
deploy_prod:
stage: deploy
script:
##将代码同步到线上服务器的/www/目录下
- rsync -avztH -e "ssh -p $PROD_ADDRES_PORT" --exclude ".git" --delete ./ $PROD_ADDRES_IP:/www/${PROJECT_NAME}/
#when(什么时候执行) manual表示手动执行job的时候触发
when: manual
only:
#表示只有打了tags之后,才会触发
- tags
tags:
- vpc
environment:
name: prod
url: $DOMAIN
#允许生成失败。失败的构建不会导致提交状态。默认是true,这里表示不允许失败
allow_failure: false
实现的功能:
当代码提交到develop分支的时候,自动将develop分支代码同步到测试服务器的/develop目录
当代码提交到test分支的时候,自动将test分支代码同步到测试服务器的/www目录
当代码提交到master分支的时候,必须要先手动打tag,然后点击CI/CD的tags任务
等到任务完成之后,自动将master分支代码同步到线上服务器的/www目录
kb-rsync的Dockerfile
# mkdir -p /opt/docker/kb-rsync
# vim /opt/docker/kb-rsync/Dockerfile
内容如下:
FROM docker.io/alpine
RUN echo "#aliyun" > /etc/apk/repositories
RUN echo "https://mirrors.aliyun.com/alpine/v3.6/main/" >> /etc/apk/repositories
RUN echo "https://mirrors.aliyun.com/alpine/v3.6/community/" >> /etc/apk/repositories
RUN apk update
RUN apk add openssh-client rsync
开始制作镜像
# docker build -t kb-rsync /opt/docker/kb-rsync
由于CI执行的任务依赖于runner,下一篇文章详细介绍,如何注册runner