gitlab-ci 持續集成完整實踐

借著公司代碼庫遷移到私有Gitlab的契機,我接下持續集成的工作,實現了對Python服務端代碼的單元測試、靜態代碼分析和接口測試的持續集成??傮w架構如下:

架構圖

執行過程:

  1. 開發提交代碼后,自動觸發gitlab-runner拉取executor鏡像執行單元測試,單元測試代碼中包含上傳測試結果到x-utest測試平臺;

  2. 單元測試通過后,gitlab-runner拉取sonar-scanner鏡像執行靜態代碼分析,分析結果評論在commit中或保存于sonarqube;

  3. 靜態代碼分析結束,執行分發操作,將代碼分發至灰度測試服務器,并運行;

  4. 執行接口測試,執行完成后上傳測試結果到x-utest測試平臺。

四個任務相互依賴,只在前一個任務狀態為成功情況下才會執行。

本文主要描述一些技術實現,會適當貼出代碼,可能能為相關從業者提供靈感與解決方案,不保證每個細節都深入講解。

Gitlab CI 基本配置

針對某個需要做CI/CD的項目,需要將代碼庫的該設置打開,并為其配置 gitlab-runner。

gitlab runner

gitlab-runner不僅可以運行在物理機,還可以運行在容器中。考慮到gitlab-runner消耗的資源少,使用容器更合適。

拉取gitlab-runner Docker 鏡像:

sudo docker pull gitlab/gitlab-runner

啟動容器:

sudo docker run -d --name gitlab-runner --restart always \
    -v /srv/gitlab-runner/config:/etc/gitlab-runner \
    -v /var/run/docker.sock:/var/run/docker.sock \
    gitlab/gitlab-runner:latest

在容器中執行register操作,將gitlab上的項目注冊到gitlab-runner中:

sudo docker exec -it gitlab-runner gitlab-ci-multi-runner register

輸入上述命令后會有一系列的配置需要輸入,當然也可以設置完后進行更改
按照提示輸入即可,前兩項可以在指定項目設置中CI/CD選項里的Runners settings選項中的Specific Runners里看到,tags是gitlab-ci.yml文件中所要用到的,executor選擇docker
配置成功后,我們可以在設置中CI/CD選項里的Runners settings選項中的Specific Runners里看到runner信息

本地executor鏡像

為了部署與測試,需要一個鏡像用于執行。當選用本地鏡像時,會發現如下報錯

拉取鏡像失敗

報錯的原因在于,gitlab-runner嘗試去官方的docker hub倉庫拉取鏡像。通過修改gitlab-runner中的配置,設置只拉取本地鏡像:

修改 /etc/gitlab-runner/config.toml ,在 [runners.docker] 下,添加:

pull_policy = never  # 該配置默認always,即只在線上拉取鏡像

如果有需要添加一些hosts映射,仍然在 [runners.docker] 下,添加:

extra_hosts = ["hostname:ip"]

另外為了加快單元測試執行速度,將服務端代碼的依賴提前安裝至executor鏡像中:

COPY requirement.txt .
RUN pip install -r requirement.txt

編寫 .gitlab-ci.yaml

單元測試部分

用nose執行測試

對于Python,nosetest工具可以嗅探與執行你寫的所有測試用例,并輸出結果。在執行測試前,使用nose需要使用pip安裝

pip install nose

安裝完成后,使用 nosetests 執行。

nosetests

自寫測試入口

另一個執行測試的選擇,是自寫測試入口,不依賴nose。好處是能夠將測試結果上傳至x-utest。
對測試結果做判斷,如果全部用例通過(即wasSuccessful為True),則sys.exit(0),否則sys.exit(1)

redis與mongo服務化

對于redis與mongo這種外部服務,有兩種解決方式,一是mock對數據庫的讀寫,二是使用服務化的redis與mongo,保證外部環境的一致性。(更推薦第一種方式,此處介紹第二種。)

由于設置了不從docker hub拉取鏡像,因此需要先拉取redis與mongo服務鏡像到本地

docker pull redis:2.8
docker pull mongo:3.2

在gitlab-ci.yaml中添加services:

services:
  - redis:2.8
  - mongo:3.2

修改代碼的local_config配置文件中的mongo與redis連接URL,指向“mongo”與“redis”

靜態代碼分析

sonarqube搭建

制做了一個docker-compose項目可以一鍵部署SonarQube平臺 <==歡迎fork/start,使用postgres作為后端數據庫,并將數據持久化在宿主機本地。

git clone https://github.com/ityoung/sonarqube-docker.git
pip install docker-compose
cd sonarqube-docker
docker-compose up

sonar scanner配置

同時我也針對Python開源了sonar-scanner鏡像的Dockerfile <==歡迎fork/start,該鏡像已經安裝pylint,方便做Python的靜態代碼分析。

git clone https://github.com/ityoung/sonar-scanner-docker.git
cd sonar-scanner-docker
docker build -t sonar-scanner .

YAML添加執行命令

啟動SonarQube后,進入IP:9000到SonarQube管理頁面,登錄admin/admin,新建一個項目,按步驟執行完成

創建一個project

創建完成后,獲取到執行代碼,復制這段代碼,添加到yaml中,能夠實現分析結果上傳到SonarQube。

獲取sonar-scanner執行腳本

注意:如果yaml中用到了兩個鏡像,盡量不要有before_script,否則可能兩個鏡像,觸發錯誤。

Sonar分析后評論

對于develop分支,可以不保存分析結果,而改為將分析結果評論在當次commit下。

在yaml腳本中添加如下參數:

    - sonar-scanner
      -Dsonar.analysis.mode=preview
      -Dsonar.gitlab.commit_sha=$CI_BUILD_REF
      -Dsonar.gitlab.ref_name=$CI_BUILD_REF_NAME
      -Dsonar.gitlab.project_id=$CI_PROJECT_ID

注意:無新issue時默認不會評論,需要在SonarQube修改gitlab配置才會每次都評論。

持續交付

這部分交由對服務端部署更熟悉的運維操作,因此不做贅述。

接口測試

接口測試代碼在另一個倉庫,這就涉及到從另一個倉庫clone測試代碼時的權限問題。

給倉庫URL添加token能夠實現跨倉庫clone代碼:

git clone https://gitlab-ci-token:${CI_JOB_TOKEN}@gitlab.xxx.com/yx/apitest.git

附一:完整的.gitlab-ci.yml

image: pro1_executor

stages:
  - unittest
  - analyze
  - deploy
  - apitest

variables:
  SONAR_HOST: "http://192.168.0.29:9000"
  SONAR_PROJ: "pro_1"
  SONAR_LOGIN: "b3135dd602b61ce7ff5f4202a3ec2ec0865fa7f5"

services:
  - redis:3
  - mongo:3.2

UnitTest:
  stage: unittest
  script:
  - pip install nose
  - python -m runtest xtest

Sonar_Preview:
  image: sonar-scanner
  stage: analyze
  script:
    - sonar-scanner
      -Dsonar.analysis.mode=preview
      -Dsonar.gitlab.commit_sha=$CI_BUILD_REF
      -Dsonar.gitlab.ref_name=$CI_BUILD_REF_NAME
      -Dsonar.gitlab.project_id=$CI_PROJECT_ID
      -Dsonar.projectKey=$SONAR_PROJ
      -Dsonar.sources=.
      -Dsonar.host.url=$SONAR_HOST
      -Dsonar.login=$SONAR_LOGIN
  except:
    - master

Sonar_Analyze:
  image: sonar-scanner
  stage: analyze
  script:
    - sonar-scanner
      -Dsonar.projectKey=$SONAR_PROJ
      -Dsonar.sources=.
      -Dsonar.host.url=$SONAR_HOST
      -Dsonar.login=$SONAR_LOGIN
  only:
    - master

Deploy_TestServer:
  stage: deploy
  script: echo "deploy"

API_Test:
  stage: apitest
  script:
    - cd /
    - git clone https://gitlab-ci-token:${CI_JOB_TOKEN}@gitlab.xxx.com/yx/apitest.git
    - cd apitest
    - pip install -r requirements.txt
    - python runtest.py

參考

[1] how to access multiple repositories in CI build?, Stack Overflow

最后編輯于
?著作權歸作者所有,轉載或內容合作請聯系作者
平臺聲明:文章內容(如有圖片或視頻亦包括在內)由作者上傳并發布,文章內容僅代表作者本人觀點,簡書系信息發布平臺,僅提供信息存儲服務。
  • 序言:七十年代末,一起剝皮案震驚了整個濱河市,隨后出現的幾起案子,更是在濱河造成了極大的恐慌,老刑警劉巖,帶你破解...
    沈念sama閱讀 230,563評論 6 544
  • 序言:濱河連續發生了三起死亡事件,死亡現場離奇詭異,居然都是意外死亡,警方通過查閱死者的電腦和手機,發現死者居然都...
    沈念sama閱讀 99,694評論 3 429
  • 文/潘曉璐 我一進店門,熙熙樓的掌柜王于貴愁眉苦臉地迎上來,“玉大人,你說我怎么就攤上這事。” “怎么了?”我有些...
    開封第一講書人閱讀 178,672評論 0 383
  • 文/不壞的土叔 我叫張陵,是天一觀的道長。 經常有香客問我,道長,這世上最難降的妖魔是什么? 我笑而不...
    開封第一講書人閱讀 63,965評論 1 318
  • 正文 為了忘掉前任,我火速辦了婚禮,結果婚禮上,老公的妹妹穿的比我還像新娘。我一直安慰自己,他們只是感情好,可當我...
    茶點故事閱讀 72,690評論 6 413
  • 文/花漫 我一把揭開白布。 她就那樣靜靜地躺著,像睡著了一般。 火紅的嫁衣襯著肌膚如雪。 梳的紋絲不亂的頭發上,一...
    開封第一講書人閱讀 56,019評論 1 329
  • 那天,我揣著相機與錄音,去河邊找鬼。 笑死,一個胖子當著我的面吹牛,可吹牛的內容都是我干的。 我是一名探鬼主播,決...
    沈念sama閱讀 44,013評論 3 449
  • 文/蒼蘭香墨 我猛地睜開眼,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了?” 一聲冷哼從身側響起,我...
    開封第一講書人閱讀 43,188評論 0 290
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎,沒想到半個月后,有當地人在樹林里發現了一具尸體,經...
    沈念sama閱讀 49,718評論 1 336
  • 正文 獨居荒郊野嶺守林人離奇死亡,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內容為張勛視角 年9月15日...
    茶點故事閱讀 41,438評論 3 360
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發現自己被綠了。 大學時的朋友給我發了我未婚夫和他白月光在一起吃飯的照片。...
    茶點故事閱讀 43,667評論 1 374
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖,靈堂內的尸體忽然破棺而出,到底是詐尸還是另有隱情,我是刑警寧澤,帶...
    沈念sama閱讀 39,149評論 5 365
  • 正文 年R本政府宣布,位于F島的核電站,受9級特大地震影響,放射性物質發生泄漏。R本人自食惡果不足惜,卻給世界環境...
    茶點故事閱讀 44,845評論 3 351
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望。 院中可真熱鬧,春花似錦、人聲如沸。這莊子的主人今日做“春日...
    開封第一講書人閱讀 35,252評論 0 28
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽。三九已至,卻和暖如春,著一層夾襖步出監牢的瞬間,已是汗流浹背。 一陣腳步聲響...
    開封第一講書人閱讀 36,590評論 1 295
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機就差點兒被人妖公主榨干…… 1. 我叫王不留,地道東北人。 一個月前我還...
    沈念sama閱讀 52,384評論 3 400
  • 正文 我出身青樓,卻偏偏與公主長得像,于是被迫代替她去往敵國和親。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當晚...
    茶點故事閱讀 48,635評論 2 380

推薦閱讀更多精彩內容