qinfengge

qinfengge

醉后不知天在水,满船清梦压星河
github
email
telegram

gitlab 的CI/CD 流水線初體驗

CI/CD#

關於 CI/CD 的理念與解釋這裡就不說了,可以看這篇文章

為什麼選擇 gitlab 的流水線#

原因也很簡單,公司的代碼托管在 gitlab 上,且 gitlab 的 free 額度好像還挺高。
不選擇Jenkins的原因也很簡單,UI 過時,功能雖多但佔用也高。
如果是新手的話 Drone 可能也很好?畢竟有可視化界面,且佔用也很小。

註冊 runner#

如果你只是想測試或者嘗鮮,那不註冊而使用共享的 runner 也是可以的。
但如果是要部署在自己的伺服器上則一定要使用註冊的 runner。
runner 的註冊方式一般有 2 種
docker

docker run -d --name gitlab-runner --restart always \\n  -v /home/jk/docker/gitlabRunner/config:/etc/gitlab-runner \\n  -v /var/run/docker.sock:/var/run/docker.sock \\n  gitlab/gitlab-runner:latest

注意 docker 方式註冊的 runner 無法在宿主機層面部署新的容器。dind (docker in docker) 相當於多嵌了一層,所以它只適合構建而不適合部署
shell

sudo curl -L --output /usr/local/bin/gitlab-runner https://gitlab-runner-downloads.s3.amazonaws.com/latest/binaries/gitlab-runner-linux-amd64
sudo chmod +x /usr/local/bin/gitlab-runner
sudo useradd --comment 'GitLab Runner' --create-home gitlab-runner --shell /bin/bash
sudo gitlab-runner install --user=gitlab-runner --working-directory=/home/gitlab-runner
sudo gitlab-runner start
sudo gitlab-runner register --url https://gitlab.com/ --registration-token {gitlab註冊runner的token}
sudo gpasswd -a gitlab-runner docker

shell 模式可以在宿主機拉取並運行 docker 鏡像,適合部署服務
更詳細的安裝教程可以查看官方文檔

創建配置文件#

你可以在 gitlab 項目中的 構建 ---> 流水線編輯器 中新建配置文件,或使用官方的配置模板

image
配置文件的命名固定為 .gitlab-ci.yml,且必須放在項目的根目錄下

image
.gitlab-ci.yml有其指定的關鍵字與格式,你可以在此處查看官方的語法文檔
常用的關鍵字如下

關鍵字說明用法
image指定流水線需要的 Docker 鏡像image: docker:latest
services指定的附加鏡像services:- name: docker:dind
variables定義全局參數variables:PORT: 9005
stages定義流水線階段stages:- build - docker-build
tags指定此階段要使用的 runnertags: - shell-node
artifacts作業產物,使用 build 命令會產生文件,此關鍵字可保存構建後的文件 artifacts:paths:- target/jk_testing-1.0-SNAPSHOT.jar
script指定此階段要運行命令腳本 script:- mvn clean install

當然,gitlab 也提供了相當多的變量以供使用
$CI_COMMIT_SHORT_SHA 表示本次提交的特徵值,你也可以使用 variables 中的自定義變量
也可以在官方文檔查看全部的變量

我非常建議您使用 Dockerfile 將您的項目打包成 docker 鏡像,這將會使它比較容易管理及部署。

例子#

下面我將用一個 spring boot 項目來為您解釋配置文件。我會盡量增加註釋

# 指定流水線需要的 Docker 鏡像
image: docker:latest

# 指定的附加鏡像
services:
- name: docker:dind

# 參數定義
variables:
  PORT: 9005
  APPLICATION_NAME: test


# 定義流水線階段
stages:
  - build
  - docker-build
  - deploy
  - notify


# 構建階段:執行 Maven 構建
build:
  image: maven:3.6.3-openjdk-8
  stage: build
  # 定義執行腳本
  script:
    - mvn clean install
  artifacts:
    paths:
    - target/jk_testing-1.0-SNAPSHOT.jar

# Docker 構建階段:構建 Docker 鏡像並推送到鏡像庫
docker-build:
  stage: docker-build
  script:
    - docker build -t $APPLICATION_NAME .
    - docker tag $APPLICATION_NAME $CI_REGISTRY_IMAGE:$CI_COMMIT_SHORT_SHA
    - docker login -u $CI_REGISTRY_USER -p $CI_REGISTRY_PASSWORD $CI_REGISTRY
    - docker push $CI_REGISTRY_IMAGE:$CI_COMMIT_SHORT_SHA

# 部署階段:滾動更新鏡像
deploy:
  stage: deploy
  # 指定註冊方式為shell的runner
  tags:
    - shell-node
  script:
    # 定義多段腳本
    # 先停止name中包含test的容器,再刪除容器和鏡像
    # 然後從鏡像庫拉取最新的鏡像並運行
    - >
      if [[ $(docker ps -q -f name=$APPLICATION_NAME) ]]; then
      docker stop $APPLICATION_NAME 2>/dev/null;
      docker rm $APPLICATION_NAME 2>/dev/null;
      docker images | grep test | awk '{print $3}' | xargs -I {} docker rmi {};
      fi
    - docker login -u $CI_REGISTRY_USER -p $CI_REGISTRY_PASSWORD $CI_REGISTRY
    - docker pull $CI_REGISTRY_IMAGE:$CI_COMMIT_SHORT_SHA
    - docker run -d -p $PORT:9004 --name $APPLICATION_NAME $CI_REGISTRY_IMAGE:$CI_COMMIT_SHORT_SHA

# 構建失敗時的通知消息
notifyFailWeChat:
  stage: notify
  script:
    - apk add curl
    - curl 'https://qyapi.weixin.qq.com/cgi-bin/webhook/send?key= {微信機器人token}' -H 'Content-Type:application/json' -d "{\"msgtype\":\"markdown\",\"markdown\":{\"content\":\"小程序項目構建結果:<font color=\\"warning\\">失敗</font>\n>本次構建由:$GITLAB_USER_NAME 觸發\n>項目名稱:$CI_PROJECT_NAME\n>提交號:$CI_COMMIT_SHA\n>提交日誌:$CI_COMMIT_MESSAGE\n>構建分支:$CI_COMMIT_BRANCH\n>流水線地址:[$CI_PIPELINE_URL]($CI_PIPELINE_URL)\"}}"
  # 指定僅master分支運行
  only:
    - master
  # 指定什麼時候執行,此處為流水線構建失敗時執行
  when: on_failure

# 構建成功時的通知消息
notifySuccessWeChat:
  stage: notify
  script:
    - apk add curl
    - curl 'https://qyapi.weixin.qq.com/cgi-bin/webhook/send?key= {微信機器人token}' -H 'Content-Type:application/json' -d "{\"msgtype\":\"markdown\",\"markdown\":{\"content\":\"小程序項目構建結果:<font color=\\"info\\">成功</font>\n>本次構建由:$GITLAB_USER_NAME 觸發\n>項目名稱:$CI_PROJECT_NAME\n>提交號:$CI_COMMIT_SHA\n>提交日誌:$CI_COMMIT_MESSAGE\n>構建分支:$CI_COMMIT_BRANCH\n>流水線地址:[$CI_PIPELINE_URL]($CI_PIPELINE_URL)\"}}"
  only:
    - master
  when: on_success

載入中......
此文章數據所有權由區塊鏈加密技術和智能合約保障僅歸創作者所有。