天天看點

群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器

常用指令

sudo -i然後輸入密碼登入root賬戶(群晖預設隻能使用admin賬号登陸)

vim xxx編輯(編輯是進去之後按i,退出并儲存是按esc,然後:wq!再回車)

mkdir xx建立檔案夾
           

準備

1. 群晖一般預設安裝docker

我們不需要進行安裝,如果沒有安裝,則去套件中心進行安裝即可
           

2. 域名

這個不做詳細贅述 比如,此文中域名是www.mydomain.com
           

3. 檔案夾權限

在群晖的volume2的docker檔案夾下建立/volume2/docker/gitea/data、/volume2/docker/gitea/data、/volume2/docker/harbor/common/config,并賦予Everyone權限
           
群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器
群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器
群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器
群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器

4. root權限

drone的deploy步驟需要root權限來進行docker釋出,是以需要群晖的root也開一下,但是群晖預設關閉root
           
ssh中sudo -i進入root權限
vim /etc/ssh/sshd_config
将#PermitRootLogin 這一行去掉注釋,修改為PermitRootLogin yes
儲存退出,然後執行synouser --setpw root xxxxxx  (xxxxxx就是你的root密碼)
reboot重新開機群晖即可
           

安裝PostgreSQL

執行下面的語句,安裝postgres資料庫,安裝成功之後,使用者名是postgres,密碼是postgrespw,端口号是14332,初始資料庫是postgres
docker run --name postgres -e POSTGRES_PASSWORD=postgrespw -v /volume2/docker/postgres/data:/var/lib/postgresql/data -d -p 14332:5432 postgres
執行成功之後我們可以使用導航貓(navicat)連接配接試一下,連接配接成功之後添加一個gitea資料庫
           

安裝gitea

執行下面的語句,安裝gitea
docker run -d --name=gitea -p 10022:22 -p 13000:3000 -v /volume2/docker/gitea/data:/data gitea/gitea
           

安裝成功之後進入http://www.mydomain.com:13000,此時是一個gitea初始化的界面設定資料庫連接配接是postgresql,資料庫名稱是gitea;修改站點名稱,伺服器域名www.mydomain.com,http端口3000,基礎URL:http://www.mydomain.com:13000/ , 管理者賬号密碼填寫gitea賬号密碼(比如賬号是myusername),郵箱寫一個然後點選安裝

安裝成功之後我們将進入http://www.mydomain.com:13000,輸入賬号密碼進入,建立一個倉庫,這個倉庫可以是從其他網站倉庫位址拉過來的,拉取過來的倉庫隻有隻讀權限,我們需要将倉庫更改為普通倉庫(在倉庫設定=>危險操作區=>轉移倉庫所有權),否則會造成無法送出的問題(gitea mirror repository is read-only)

群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器

下一步,進行drone設定,此時我們的drone未安裝,但是我們将14000端口配置設定給它使用,也就是http://www.mydomain.com:14000

點選頭像(右上角)=>設定=>應用=>建立新的 OAuth2 應用程式,應用名稱填寫drone,重定向 URI填寫http://www.mydomain.com:14000/login,點選建立應用,記錄一下client-id、client-secret

安裝drone

在安裝之前,我們可以先執行一下

openssl rand -hex 16

來擷取一個共享的key,這個key值我們下面将使用到(當然也可以使用其他方法來随機擷取一個加密程度更高的key)

安裝drone server

docker run \
  --volume=/var/lib/drone:/data \
  --env=DRONE_GITEA_SERVER=http://www.mydomain.com:13000 \
  --env=DRONE_GITEA_CLIENT_ID=client-id \
  --env=DRONE_GITEA_CLIENT_SECRET=client-secret \
  --env=DRONE_RPC_SECRET=共享的key \
  --env=DRONE_SERVER_HOST=www.mydomain.com:14000 \
  --env=DRONE_DATABASE_DRIVER=postgres \
  --env=DRONE_DATABASE_DATASOURCE=postgres://postgres:[email protected]:14332/postgres?sslmode=disable \
  --env=DRONE_SERVER_PROTO=http \
  --publish=14000:80 \
  --publish=14443:443 \
  --restart=always \
  --detach=true \
  --name=drone \
  --env=DRONE_USER_CREATE=username:myusername,admin:true \
  drone/drone:2
  
           

安裝drone-runner

docker run --detach \
  --volume=/var/run/docker.sock:/var/run/docker.sock \
  --env=DRONE_RPC_PROTO=http \
  --env=DRONE_RPC_HOST=www.mydomain.com:14000 \
  --env=DRONE_RPC_SECRET=共享的key \
  --env=DRONE_RUNNER_CAPACITY=2 \
  --env=DRONE_RUNNER_NAME=test-runner \
  --env=DRONE_AGENTS_ENABLED=true \
  --publish=14300:3000 \
  --restart=always \
  --name=runner \
  drone/drone-runner-docker:1
  
           

安裝成功之後,進入http://www.mydomain.com:14000,應該可以看到剛才我們在gitea建立的倉庫了

群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器

在此時的gitea裡面,我們在這個項目的設定=>Web 鈎子裡面能看到一個網址連接配接,這個網址連接配接就指向的是drone

群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器

點選倉庫進去,在settings裡面打開Trusted

群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器

然後在左下角的setting裡面添加使用者test-runner(對應drone-runner安裝裡面的DRONE_RUNNER_NAME)

群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器

此時,我們的gitea和drone已經OK了,我們來安裝一下harbor

安裝harbor

1. 安裝過程

參考使用Harbor搭建Docker私有鏡像倉庫,去[goharbor/harbor/releases (https://github.com/goharbor/harbor/releases)下載下傳一下最新版的harbor-offline-installer-vx.x.x.tgz,建議首先

cd /volume2/docker
wget https://github.com/goharbor/harbor/releases/download/v1.10.11/harbor-offline-installer-v1.10.11.tgz
tar -zxvf harbor-offline-installer-v1.10.11.tgz
cd harbor
mkdir common
cd common
mkdir config
cd /volume2/docker/harbor
vim harbor.yml  //修改一下hostname和port,比如hostname:www.mydomain.com , port:19080, 然後儲存退出
sudo ./install.sh //最後會輸出`Harbor has been installed  and started successfully`,說明安裝成功
           

我們進入http://www.mydomain.com:19080,然後輸入賬号admin,密碼Harbor12345,進入後去更改一下密碼(!!!注意,此時的密碼不能有特殊符号,否則不會儲存,更改harbor.yml時,裡面的所有密碼最好不要随意更改)

然後去系統設定=>使用者管理新增一個使用者(使用者名:myharborname,密碼:myharborpw),便于一會兒進行docker的操作

同時點選項目=>library=>成員=>添加使用者,将myharborname添加進來,權限設定成項目管理者(否則有可能出現publish階段的denied: requested access to the resource is denied問題,該問題也可以通過

docker login www.mydomain.com:19080

登陸一下來嘗試解決)

群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器

2. 問題

  1. 如果出現了harbor-db容器經常重新開機的問題,可以通過

    docker logs --tail="100" harbor-db //檢視最近100行日志

    ,如果日志是

    could not write lock file "postmaster.pid": No space left on device

    或者通過

    cat /var/log/harbor/postgresql.log | tail -20

    查出來的日志包含

    could not close temporary statistics file "pg_stat_tmp/db_12406.tmp": No space left on device

    ,那說明docker送出太頻繁導緻記憶體不足,
cat /volume2/docker/harbor/docker-compose.yml --檢視一下postgresql的映射路徑,發現是/data/database
cd /data/database
rm -rf /data/database
cd /data
mkdir database
cd /volume2/docker/harbor
docker-compose down -v --關閉所有的harbor容器
cd /volume2/docker/harbor/common/config
rm -rf *
cd /volume2/docker/harbor
sudo ./install.sh --重新安裝一下,密碼、使用者等需要重新添加一次 
           
  1. 如果出現了http://www.mydomain.com:19080登陸報錯500,那麼一般去重新開機一下harbor的nginx容器即可

CI和CD

我們再去drone中剛才的倉庫中setting=>Secret新增兩個Secret

分别是:

docker_username 值:myharborname ; docker_password 值:myharborpw

群晖下 gitea+drone+harbor實作CI/CD 釋出到雲伺服器

之前的倉庫我們拉取到本地,推薦使用Sourcetree,拉取之後在倉庫的根目錄下面建立兩個檔案.drone.yml和Dockerfile

我這裡使用的是.net 6,所有Dockerfile内容:

FROM mcr.microsoft.com/dotnet/aspnet:6.0
COPY . .
WORKDIR /app
EXPOSE 29029/tcp
ENTRYPOINT ["dotnet", "k8s-netcore-demo.dll"]
           

.drone.yml的内容:

kind: pipeline
type: docker
name: deployment

steps:
- name: ls
  image: alpine
  commands:
  - ls -la
  - ls -la Dockerfile  --檢視目前檔案夾是否包含了Dockerfile
- name: build
  image: mcr.microsoft.com/dotnet/sdk:6.0
  commands:
  - dotnet restore
  - dotnet build -c Release -o /drone/src_temp/k8s-netcore-demo/ --no-restore  --build之後的檔案輸出到/drone/src_temp/k8s-netcore-demo/目錄中,因為項目檔案預設在/drone/src/目錄,而build預設輸出也是/drone/src/,我們後面釋出到docker裡面隻需要釋出build的檔案即可,是以先輸出到臨時目錄
  - mv /drone/src/Dockerfile /drone/src_temp/k8s-netcore-demo/ --将項目檔案目錄中的Dockerfile也移動到臨時目錄
  - rm -rf *   --删除項目檔案/drone/src/下面的所有檔案
  - mv /drone/src_temp/k8s-netcore-demo/* /drone/src  --将臨時目錄的檔案移動到drone執行的預設目錄中
  - ls -la  --檢視最後的/drone/src/下檔案,可以驗證一下是不是build之後+Dockerfile檔案
  - pwd  --輸出目前檔案夾路徑
  - echo 項目生成成功
- name: publish 2 harbor
  image: plugins/docker
  settings: 
    dockerfile: Dockerfile
    tags: latest
    insecure: true
    registry: www.mydomain.com:19080
    repo: www.mydomain.com:19080/library/k8s-netcore-demo
    storage_driver: vfs
    username: 
      from_secret: docker_username
    password: 
      from_secret: docker_password
- name: deploy
  image: appleboy/drone-ssh
  pull: true
  settings:
    host: 雲伺服器IP
    port: 22
    username: root
    password: root密碼
    command_timeout: 2m
    script: 
      - source /etc/profile
      - ls -la
      - docker info
      - echo $(docker ps -aqf "name=k8s-netcore-demo")
      - docker stop $(docker ps -aqf "name=k8s-netcore-demo")
      - docker container rm k8s-netcore-demo
      - docker rmi k8s-netcore-demo
      - echo 檢視是否成功删除k8s-netcore-demo
      - docker ps -a
      - echo 從harbor拉取docker鏡像
      - sudo docker container rm xxxxxx/k8s-netcore-demo
      - sudo docker pull www.mydomain.com:19080/library/k8s-netcore-demo:latest
      - sudo docker tag www.mydomain.com:19080/library/k8s-netcore-demo:latest xxxxxx/k8s-netcore-demo:latest
      - sudo docker run --name k8s-netcore-demo -d -p 29029:80 xxxxxx/k8s-netcore-demo
      - /usr/local/bin/docker system prune -f
      - echo docker容器啟動成功 
//可增加 branches: [ master ] #隻對master代碼觸發部署
           

這裡簡單解釋一下

  1. image: mcr.microsoft.com/dotnet/aspnet:6.0,原來的Gogs + Drone 實作CI/CD(CD)中image是microsoft/dotnet,但是實際會出現錯誤(Error response from daemon: pull access denied for microsoft/dotnet, repository does not exist or may require 'docker login': denied: requested access to the resource is denied),從Unable to build pipeline: pull access denied for microsoft/dotnet, repository does not exist or may require 'docker login': denied: requested access中找到問題,是因為微軟把docker庫遷走了,這個倉庫沒有對應的dotnet鏡像了。。。是以我們要根據自己的項目版本自己去更改, 不要使用mcr.microsoft.com/dotnet/aspnet:6.0,要使用sdk
  2. dockerfile: Dockerfile這裡我沒有使用drone-ci-demo/Dockerfile,因為Dockerfile其實是在根目錄下,可以檢視name: ls的輸出,查閱問題連結unable to evaluate symlinks in Dockerfile path: lstat /drone/src/Dockerfile: no such file or directory
  3. 增加storage_driver: vfs,解決連結Plugins/Docker on Synology DSM
  4. 因為群晖預設沒有開root,是以要按照準備工作第三步進行操作,打開root,如果使用admin賬号,則會出現權限問題,是因為admin不能在ssh中調用docker和其他script指令(第一次嘗試我是按照部署到群晖執行的(群晖的dotnet SDK安裝之後軟連接配接好像有問題,無法執行),是以有上面的一句話,如果釋出到雲伺服器,可以給其他賬戶開權限,這樣就不必使用root賬戶了)

其他

1. 群晖與其他linux的不同

#### 1. docker的daemon.json位址
          不是`/etc/docker/daemon.json`,而是`/var/packages/Docker/etc/dockerd.json`
   #### 2. 常用指令不是`systemctl`或者`service`
          常用指令不是`systemctl`或者`service`,而是`synoservice`,前面加一個`syno`,可以通過`synoservicecfg --list`檢視群晖下運作的所有服務,其中套件中心的服務前面需要加`pkgctl-`作為字首,例如`synoservice –restart pkgctl-Docker`
           

2. 雲伺服器安裝dotnet,自己可以去查閱微軟的文檔 在 Linux 發行版上安裝 .NET

參考連結

https://discourse.drone.io/

https://plugins.drone.io/plugins/docker

https://65535.pub/2020/06/01/gitea-drone-群晖搭建/

https://www.cnblogs.com/fallTakeMan/p/11944042.html

https://www.cnblogs.com/fallTakeMan/p/11866584.html

https://www.cnblogs.com/fallTakeMan/p/11875846.html

https://www.hafuhafu.cn/267/

https://www.cnblogs.com/manastudent/p/15938616.html

https://www.msnao.com/2019/04/26/568.html