通過 gitlab 安裝 CD

我曾經想過自動化我的項目的部署。 gitlab.com 慷慨地提供了所有這方面的工具,當然我決定通過弄清楚並編寫一個小型部署腳本來使用它。 在這篇文章中,我與社區分享了我的經驗。

TL博士

  1. 設置VPS:禁用root、密碼登錄、安裝dockerd、配置ufw
  2. 為服務器和客戶端生成證書 docs.docker.com/engine/security/https/#create-a-ca-server-and-client-keys-with-openssl 通過 tcp 套接字啟用 dockerd 控制:從 docker 配置中刪除 -H fd:// 選項。
  3. 在 docker.json 中設置證書的路徑
  4. 使用證書內容在 CI / CD 設置中的 gitlab 變量中註冊。 編寫 .gitlab-ci.yml 腳本進行部署。

我將展示 Debian 發行版上的所有示例。

初始 VPS 設置

例如,您在這裡購買了一個實例 DO,首先要做的就是保護您的服務器免受外界的攻擊。 我不會證明或斷言任何內容,我只會顯示我的虛擬服務器的 /var/log/messages 日誌:

截圖通過 gitlab 安裝 CD

首先,安裝ufw防火牆:

apt-get update && apt-get install ufw

啟用默認策略:阻止所有傳入連接,允許所有傳出連接:

ufw default deny incoming
ufw default allow outgoing

重要提示:不要忘記允許通過 ssh 連接:

ufw allow OpenSSH

一般語法為:允許端口上的連接:ufw allowed 12345,其中 12345 是端口號或服務名稱。 拒絕:ufw拒絕12345

開啟防火牆:

ufw enable

我們退出會話並通過 ssh 再次登錄。

添加一個用戶,為其分配密碼,並將其添加到 sudo 組。

apt-get install sudo
adduser scoty
usermod -aG sudo scoty

接下來,根據計劃,您應該禁用密碼登錄。 為此,請將 ssh 密鑰複製到服務器:

ssh-copy-id [email protected]

服務器的ip必須是你的。 現在嘗試使用之前創建的用戶登錄,無需再輸入密碼。 接下來,在配置設置中,更改以下內容:

sudo nano /etc/ssh/sshd_config

禁用密碼登錄:

PasswordAuthentication no

重新啟動 sshd 守護進程:

sudo systemctl reload sshd

現在,如果您或其他人嘗試以 root 身份登錄,將會失敗。

接下來,我們安裝 dockerd,我不會在這裡描述這個過程,因為一切都可以改變,按照官方網站的鏈接,完成在虛擬機上安裝 docker 的步驟: https://docs.docker.com/install/linux/docker-ce/debian/

證書生成

要遠程控制 docker 守護進程,需要加密的 TLS 連接。 為此,您需要擁有需要生成並傳輸到遠程計算機的證書和密鑰。 按照 docker 官方網站上的說明中給出的步驟進行操作: https://docs.docker.com/engine/security/https/#create-a-ca-server-and-client-keys-with-openssl 所有為服務器生成的 *.pem 文件,即 ca.pem、server.pem、key.pem,應放置在服務器上的 /etc/docker 目錄中。

碼頭工人設置

在docker daemon啟動腳本中,刪除-H df://選項,該選項告訴docker daemon可以控制在哪個主機上。

# At /lib/systemd/system/docker.service
[Service]
Type=notify
ExecStart=/usr/bin/dockerd

接下來,創建一個設置文件(如果尚不存在)並設置選項:

/etc/docker/docker.json

{
  "hosts": [
    "unix:///var/run/docker.sock",
    "tcp://0.0.0.0:2376"
  ],
  "labels": [
    "is-our-remote-engine=true"
  ],
  "tls": true,
  "tlscacert": "/etc/docker/ca.pem",
  "tlscert": "/etc/docker/server.pem",
  "tlskey": "/etc/docker/key.pem",
  "tlsverify": true
}

允許端口 2376 上的連接:

sudo ufw allow 2376

使用新設置重新啟動 dockerd:

sudo systemctl daemon-reload && sudo systemctl restart docker

讓我們檢查:

sudo systemctl status docker

如果一切都是綠色的,那麼我們就認為我們已經在服務器上成功配置了 docker。

在gitlab上設置持續交付

為了使 gitalab Worker 能夠在遠程 docker 主機上執行命令,您需要決定如何以及在何處存儲證書以及與 dockerd 的加密連接的密鑰。 我通過簡單地寫入 gitlbab 設置中的變量解決了這個問題:

劇透標題通過 gitlab 安裝 CD

只需通過 cat 輸出證書和密鑰的內容: cat ca.pem。 複製並粘貼到變量值中。

我們來寫一個腳本,通過gitlab進行部署。 將使用 docker-in-docker (dind) 鏡像。

.gitlab-ci.yml

image:
  name: docker/compose:1.23.2
  # перепишем entrypoint , чтобы работало в dind
  entrypoint: ["/bin/sh", "-c"]

variables:
  DOCKER_HOST: tcp://docker:2375/
  DOCKER_DRIVER: overlay2

services:
  - docker:dind

stages:
  - deploy

deploy:
  stage: deploy
  script:
    - bin/deploy.sh # скрипт деплоя тут

部署腳本的內容及註釋:

bin/deploy.sh

#!/usr/bin/env sh
# Падаем сразу, если возникли какие-то ошибки
set -e
# Выводим, то , что делаем
set -v

# 
DOCKER_COMPOSE_FILE=docker-compose.yml
# Куда деплоим
DEPLOY_HOST=185.241.52.28
# Путь для сертификатов клиента, то есть в нашем случае - gitlab-воркера
DOCKER_CERT_PATH=/root/.docker

# проверим, что в контейнере все имеется
docker info
docker-compose version

# создаем путь (сейчас работаем в клиенте - воркере gitlab'а)
mkdir $DOCKER_CERT_PATH
# изымаем содержимое переменных, при этом удаляем лишние символы добавленные при сохранении переменных.
echo "$CA_PEM" | tr -d 'r' > $DOCKER_CERT_PATH/ca.pem
echo "$CERT_PEM" | tr -d 'r' > $DOCKER_CERT_PATH/cert.pem
echo "$KEY_PEM" | tr -d 'r' > $DOCKER_CERT_PATH/key.pem
# на всякий случай даем только читать
chmod 400 $DOCKER_CERT_PATH/ca.pem
chmod 400 $DOCKER_CERT_PATH/cert.pem
chmod 400 $DOCKER_CERT_PATH/key.pem

# далее начинаем уже работать с удаленным docker-демоном. Собственно, сам деплой
export DOCKER_TLS_VERIFY=1
export DOCKER_HOST=tcp://$DEPLOY_HOST:2376

# проверим, что коннектится все успешно
docker-compose 
  -f $DOCKER_COMPOSE_FILE 
  ps

# логинимся в docker-регистри, тут можете указать свой "местный" регистри
docker login -u $DOCKER_USER -p $DOCKER_PASSWORD

docker-compose 
  -f $DOCKER_COMPOSE_FILE 
  pull app
# поднимаем приложение
docker-compose 
  -f $DOCKER_COMPOSE_FILE 
  up -d app

主要問題是從 gitlab CI / CD 變量中“提取”正常形式的證書內容。 我不明白為什麼與遠程主機的連接不起作用。 我查看了主機上的sudojournalctl -u docker日誌,握手有錯誤。 我決定查看變量中通常存儲的內容,為此您可以查看 cat -A $DOCKER_CERT_PATH/key.pem。 通過添加刪除插入符字符 tr -d 'r' 克服了該錯誤。

此外,您可以自行決定將發布後任務添加到腳本中。 您可以在我的存儲庫中查看工作版本 https://gitlab.com/isqad/gitlab-ci-cd

來源: www.habr.com

添加評論