Go 1.15 新增 Module cache 環境變數

golang logo

相信各位開發者在寫 Go 語言專案,現在肯定都是使用 Go module 了,而 Go Module 檔案預設寫在 /go/pkg/mod 目錄內,要串 CI/CD 流程時,由於不在專案路徑底下,所以每一個 Container 無法共用 /go/pkg/mod 路徑,造成重複下載第三方套件,其實跨容器的解決方式可以透過 DroneTemporary Volumes 方式解決,但是最終希望跑完編譯流程時,可以將最後的 mod 目錄打包留到下次的 CI/CD 部署流程使用,這時候如果可以改變 /go/pkg/mod 路徑,就可以動態調整目錄結構了。底下是針對 Drone 這套部署工具進行解說。

教學影片

如果對於課程內容有興趣,可以參考底下課程。

如果需要搭配購買請直接透過 FB 聯絡我,直接匯款(價格再減 100

GOMODCACHE 環境變數

Go 1.15 開始支援 GOMODCACHE 環境變數,此變數預設是 GOPATH[0]/pkg/mod,現在這個路徑可以透過環境變數進行修正了。本篇教學會使用 meltwater/drone-cache 套件來完成 go module 的 cache 機制,加快後續每次的 CI/CD 部署。要進行 cache 前,我們需要在 pipeline 先建立 Temporary Volumes

volumes:
- name: cache
  temp: {}

有了這個暫時性的空間,就可以在不同步驟的容器內看到相同的檔案了。接著設定編譯 Go 專案的步驟

- name: build
  pull: always
  image: golang:1.15-rc
  commands:
  - make build
  environment:
    CGO_ENABLED: 0
    GOMODCACHE: '/drone/src/pkg.mod'
    GOCACHE: '/drone/src/pkg.build'
  when:
    event:
      exclude:
      - tag
  volumes:
  - name: cache
    path: /go

這邊可以注意,由於 Go 1.15 尚未釋出 (預計 2020/08),所以先用了 rc 版本。這邊可以注意我們修改了 GOMODCACHE,將原本 mod 內容放到 /drone/src/pkg.mod/drone/src 就是專案目錄了,所以記得設定一個不會用到的目錄名稱,請使用絕對路徑。

使用 build cache

在 CI/CD 編譯流程,第一個步驟就是將遠端備份好的 mod 檔案下載到容器內,並且解壓縮到 GOMODCACHE 所指定的路徑。

- name: restore-cache
  image: meltwater/drone-cache
  environment:
    AWS_ACCESS_KEY_ID:
      from_secret: aws_access_key_id
    AWS_SECRET_ACCESS_KEY:
      from_secret: aws_secret_access_key
  pull: always
  settings:
    debug: true
    restore: true
    cache_key: '{{ .Repo.Name }}_{{ checksum "go.mod" }}_{{ checksum "go.sum" }}_{{ arch }}_{{ os }}'
    bucket: drone-cache-demo
    region: ap-northeast-1
    local_root: /
    archive_format: gzip
    mount:
      - pkg.mod
      - pkg.build
  volumes:
  - name: cache
    path: /go

這邊可以看到我是使用了 AWS S3 做為背後的 Storage,你也可以透過 SFTP 或其他方式來做變化。在 archive_format 請選擇 gzip,可以讓檔案更小些。接著會進行一系列 Go 的流程,像是測試,編譯,打包 … 等等,最後會將 pkg.mod 進行打包再上傳到 AWS S3。

- name: rebuild-cache
  image: meltwater/drone-cache
  pull: always
  environment:
    AWS_ACCESS_KEY_ID:
      from_secret: aws_access_key_id
    AWS_SECRET_ACCESS_KEY:
      from_secret: aws_secret_access_key
  settings:
    rebuild: true
    cache_key: '{{ .Repo.Name }}_{{ checksum "go.mod" }}_{{ checksum "go.sum" }}_{{ arch }}_{{ os }}'
    bucket: drone-cache-demo
    region: ap-northeast-1
    archive_format: gzip
    mount:
      - pkg.mod
      - pkg.build
  volumes:
  - name: cache
    path: /go

程式碼請參考這邊

  • 人方 張

    標題打錯了,是1.15不是1.5版。