【持續集成】GitLab CI + Docker 實現持續集成


GitLab CI + Docker 實現持續集成

一、持續集成(Continuous Integration, CI)的基本概念

概述

在傳統軟件的開發中,代碼的集成工作通常是在所有人都將工作完成后在項目即將結束進行時,而這往往會花費大量的時間和精力。而持續集成是一種將集成階段放在軟件開發階段的做法,以便更加有規律地構建,測試和集成代碼。

“持續集成並不能消除 Bug,而是讓它們非常容易發現和改正。”

持續集成可以在開發人員提交了新代碼后,立刻進行構建、單元測試。從而我們可以根據測試結果以確定新的代碼或者環境配置與原來的以及其他開發人員的代碼或者環境配置能否正確地集成在一起。

持續交付 & 持續部署

持續交付(Continuous Delivery):頻繁地將軟件的新版本,交付給質量團隊或者用戶,以供評審。如果評審通過,代碼就進入生產階段。

持續部署(Continuous Deployment):是持續交付的下一步,指的是代碼評審以后,自動部署到生產環境。

二、GitLab 持續集成起步

從 GitLab 8.0 開始,GitLab CI 就已經集成在 GitLab 中,我們只需要在項目中添加一個 .gitlab-ci.yml 文件,然后添加一個 Runner,即可進行持續集成。而且隨着 GitLab 的升級,GitLab 也變得越來越強大。

.gitlab-ci.yml

.gtilab-ci.yml 文件存放與項目於倉庫的根目錄,用以來定義 GitLab CI/CD 中的 Pipeline。其實無非是一個配置文件,理解起來挺簡單的,我們主要是需要了解 Pipeline 的概念以及如何配置一個 .gitlab-ci.yml

Pipeline & Stages & Jobs

一個 Pipeline 大概相對於一個構建任務,里面可以包含多個流程,如安裝依賴、運行測試、編譯、部署測試服務器、部署生產服務器等流程,Git 提交時會觸發 Pipeline。而一個 Pipeline 中又可以包含一至多個 Stage,即用來定義安裝依賴、運行測試之類的流程的。然后,一個 Stage 中又包含了一至多個 Job,Jobs 表示一個 Stage 中具體的構建工作,即某個 Stage 里面執行的工作。我們可以在 Stages 里面定義這些 Job,它們之間的關系如下圖所示:

注意:

  • Stages 會按 .gitlab-ci.yml 中配置的順序執行,當前面的 Stage 執行完畢后才會繼續執行后面的 Stage,如果一個 Stage 失敗,那么后面的 Stage 不會執行,該構建任務失敗。
  • Stage 中的 Jobs 會並行執行,當這個 Stage 中所有的 Job 都執行完畢,該 Stage 才算執行成功。換而言之,只要有一個 Job 執行失敗,整個 Pipeline 也就失敗了。
stages:
 - build
 - test
 - deploy
 
build:
  stage: build
  script: 
    - "execute-script-for-build"
    - "do something...""
  only:
    - master
  tags:
    - ruby
    - postage

test:
  stage: test
  script:
  
......

上面配置將一次 pipeline 分成了三個階段:build、test、deploy。下面介紹配置文件中的節點:

  • stages: 定義構建的階段;
  • build、test、...:定義 jobs_name,即在 stages 中定義的 stage 階段,一般在 stage 節點注明所屬的 stage;
  • script:Runner 執行的腳本或命令,該節點是必須的。
  • 其他節點:stage 中還有許多其他節點,例如 only、tags 等,但並不是 required ,其具體作用可在文檔中了解。

GitLab Runner

當我們理解完上面的概念后,我們還沒了解最重要的東西——上面的任務由誰來構建呢?答案就是 Gitlab-runner 了!

為什么不用 GitLab CI 來運行這些構建任務呢?

一般來說,構建任務任務都會占用很多的系統資源(譬如編譯代碼),而 GitLab CI 又是 GitLab 的一部分,如果由 GitLab CI 來運行構建任務的話,在執行構建任務的時候, GitLab 的性能會大幅下降。

GitLab CI 最大的作用是管理各個項目的構建狀態,因此,運行構建任務這種浪費資源的事情就交給 GitLab Runner 來做啦!

因為 GitLab Runner 可以安裝到不同的機器上,所以在構建任務運行期間並不會影響到 GitLab 的性能。

三、持續集成的實現

接下來介紹 GitLab 對 Spring Boot 程序的持續集成,當然 GitLab 不止支持 Java 應用服務,肯定也支持其他編譯語言,這里主要只是像演示一下過程,過程基本上是相通的。

搭建 GitLab 服務

這不是本次的重點,所以就簡要介紹下咯。
利用 Docker 和 Docker Compose 快速搭建 GitLab 服務,docker-compose.yml 文件如下:

version: '3'
services:
    web:
      image: 'twang2218/gitlab-ce-zh:10.5'
      restart: always
      hostname: '192.168.253.139'
      environment:
        TZ: 'Asia/Shanghai'
        GITLAB_OMNIBUS_CONFIG: |
          external_url 'http://192.168.253.139:8080'
          gitlab_rails['gitlab_shell_ssh_port'] = 2222
          unicorn['port'] = 8888
          nginx['listen_port'] = 8080
      ports:
        - '8080:8080'
        - '8443:443'
        - '2222:22'
      volumes:
        - /usr/local/docker/gitlab/config:/etc/gitlab
        - /usr/local/docker/gitlab/data:/var/opt/gitlab
        - /usr/local/docker/gitlab/logs:/var/log/gitlab

啟動完畢后,訪問 http://ip:8080,初始化安裝完成后效果如下:

設置初始化密碼后刷新,就可以看見登錄界面了,登錄!

配置 SSH 免密登錄

ssh-keygen -t rsa -P 'youname'

復制用戶目錄下的 .ssh 文件夾下的公鑰,將其復制到 GitLab 的

構建 Docker Runner

環境准備

  • 創建工作目錄 /usr/lcoal/docker/runner
  • 創建構建目錄 /usr/local/docker/runner/enviroment
  • 下載 jdk-8u152-linux-x64.tar.gz 並復制到 /usr/local/docker/runner/environment

Dockerfile

usr/lcoal/docker/runner/environment 目錄下創建 Dockerfile

FROM gitlab/gitlab-runner:v11.0.2

RUN echo 'deb http://mirrors.aliyun.com/ubuntu/ xenial main restricted universe multiverse' > /etc/apt/sources.list && \
    echo 'deb http://mirrors.aliyun.com/ubuntu/ xenial-security main restricted universe multiverse' >> /etc/apt/sources.list && \
    echo 'deb http://mirrors.aliyun.com/ubuntu/ xenial-updates main restricted universe multiverse' >> /etc/apt/sources.list && \
    echo 'deb http://mirrors.aliyun.com/ubuntu/ xenial-backports main restricted universe multiverse' >> /etc/apt/sources.list && \
    apt-get update -y && \
    apt-get clean

RUN apt-get -y install apt-transport-https ca-certificates curl software-properties-common && \
    curl -fsSL http://mirrors.aliyun.com/docker-ce/linux/ubuntu/gpg | apt-key add - && \
    add-apt-repository "deb [arch=amd64] http://mirrors.aliyun.com/docker-ce/linux/ubuntu $(lsb_release -cs) stable" && \
    apt-get update -y && \
    apt-get install -y docker-ce

COPY daemon.json /etc/docker/daemon.json

WORKDIR /usr/local/bin
RUN wget https://raw.githubusercontent.com/topsale/resources/master/docker/docker-compose

RUN chmod +x docker-compose

RUN mkdir -p /usr/local/java
WORKDIR /usr/local/java
COPY jdk-8u152-linux-x64.tar.gz /usr/local/java
RUN tar -zxvf jdk-8u152-linux-x64.tar.gz && \
    rm -fr jdk-8u152-linux-x64.tar.gz

RUN mkdir -p /usr/local/maven
WORKDIR /usr/local/maven
RUN wget https://raw.githubusercontent.com/topsale/resources/master/maven/apache-maven-3.5.3-bin.tar.gz

RUN tar -zxvf apache-maven-3.5.3-bin.tar.gz && \
    rm -fr apache-maven-3.5.3-bin.tar.gz


ENV JAVA_HOME /usr/local/java/jdk1.8.0_152
ENV MAVEN_HOME /usr/local/maven/apache-maven-3.5.3
ENV PATH $PATH:$JAVA_HOME/bin:$MAVEN_HOME/bin

WORKDIR /

daemon.json

/usr/local/docker/runner/environment 目錄下創建 daemon.json,用於配置加速器和倉庫地址

{
  "registry-mirrors": [
    "https://registry.docker-cn.com"
  ],
  "insecure-registries": [
    "ip:port"
  ]
}

新建 Git 項目

新建一個 Git 項目,將其克隆到本地

注冊 Runner

docker exec -it gitlab-runner gitlab-runner register

# 輸入 GitLab 地址
Please enter the gitlab-ci coordinator URL (e.g. https://gitlab.com/):
http://192.168.75.146:8080/

# 輸入 GitLab Token
Please enter the gitlab-ci token for this runner:
1Lxq_f1NRfCfeNbE5WRh

# 輸入 Runner 的說明
Please enter the gitlab-ci description for this runner:
可以為空

# 設置 Tag,可以用於指定在構建規定的 tag 時觸發 ci
Please enter the gitlab-ci tags for this runner (comma separated):
可以為空

# 選擇 runner 執行器,這里我們選擇的是 shell
Please enter the executor: virtualbox, docker+machine, parallels, shell, ssh, docker-ssh+machine, kubernetes, docker, docker-ssh:
shell

以上交互中,GitLab 地址和 Token 令牌可以在 GitLab 的項目的設置中找到:

當上述步驟完成后,刷新當前頁面,可以看見當前頁面下多出來一個 runner:

完善項目

在這里我只簡單地做了個小 dome,大概這么簡單:

項目中用到的 .gitlab-ci.ymlDockerfiledocker-compose.yml 如下:
.gitlab-ci.yml

stages:
  - build
  - run
  - clean

build:
  stage: build
  script:
    - /usr/local/maven/apache-maven-3.5.3/bin/mvn clean package
    - cp target/ci-test-project-1.0.0-SNAPSHOT.jar docker
    - cd docker
    - docker build -t ci-test-project .

run:
  stage: run
  script:
    - cd docker
    - docker-compose down
    - docker-compose up -d

clean:
  stage: clean
  script:
    - docker rmi $(docker images -q -f dangling=true)

Dockerfile

FROM openjdk:8-jre

RUN mkdir /app

COPY ci-test-project-1.0.0-SNAPSHOT.jar /app/app.jar

ENTRYPOINT ["java", "-Djava.security.egd=file:/dev/./urandom", "-jar", "/app/app.jar"]

EXPOSE 8080

docker-compose.yml

version: '3.1'
services:
  itoken-config:
    restart: always
    image: ci-test-project
    ports:
      - 8080:8080

提交項目

完成 demo 的之后就將項目提交到 GitLab 上,push 完成之后,點擊項目的 CI/CD 可以看見一下頁面

再點擊進入就可以看見具體的作業了,自行體會

當項目出現所有 jobs 全部通過時,也就是持續集成初步完善了,這時我們可以打開瀏覽器訪問 ip:8080 可以看見瀏覽器上顯示

Hello GitLab

此時我們可以嘗試修改項目中的代碼再提交,比如簡單地將 retuen "Hello GitLab" 改成 return "Hello World" 再提交一遍代碼,等 jobs 通過后,再刷新瀏覽器,我們可以看見

Hello World

至此,這個小 Demo 也就完成了。

四、參考


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM