工具

[CI/CD] 利用 Github 和 Travis CI 自動上傳部署網站

CI/CD, 利用 github 和 travis ci 自動上傳部署 (rsync) 網站
CI/CD 已經漸漸成為 Web Application 必備技能、工具之一
就算沒有真的安裝、使用過 CI/CD
我也建議試用一下 github 加 travis 這個組合, 體驗一下 CI/CD 能帶來的好處與便利性

index:

前言

feature

利用 github 和 travis.org 執行一些簡單的指令(例如爬蟲), 再加上 travis 的每日任務 (Cron Jobs) 完成自動部署、更新資料的動作~~

.
.
先來看一下成果
https://cola.workxplay.net/travis-ci-auto-deploy/

當然, 這樣的內容超廢 XD
但要別忘了這是全自動建置完成的~

scenario

簡單的小工具用 PHP 抓取 政府 open API 電影資料, 找出今日活動然後顯示在頁面上…

以往~
執行爬蟲更新資料或是修改程式後需要更新線上網站內容時…
我們都需要人工輸入指令和一台空閒的機器
雖然可以把指令寫成腳本(script)簡單的一鍵完成這些動作… 但還欠一台空閒的機器去執行.
最後就是身為一個工程師當然希望能更簡單完成一整串動作… 懶還要更懶

簡單的事情複雜做
複雜的事情簡單做

讓整個部署、更新流程自動化、簡單化
(然後再省一台簡單的爬蟲機器)

當然~ 上述自動化的手續就不簡單 😓

透過下面簡單的筆記分享大家一起指道、學習~~ 😀

使用服務

  • 程式來源: https://github.com/cscolabear/travis-ci-auto-deploy
  • CI 服務: travis.org
  • 資料來源: 政府資料開放平台 https://data.gov.tw/dataset/6010

skill requirement

在建置 CI/CD 時~ 最好能有以下技能比較不會撞牆

  • shell script
  • 一些 docker 概念
  • GIT 遠端 CLI 指令
  • 因為是配合 GITHUB 平台, 最好也暸解一下 GITHUB 的權限管理

流程大綱

  1. PHP 爬蟲抓取 政府資料開放平台 – 電影類 的資料
  2. 從 API 資料中找出當天活動
  3. 暫存為靜態資料檔 (json)
  4. 利用 rsync 將資料上傳至網站 Server
  5. Slack 回報建置狀態

How

travis.org 為免費服務所以僅支援公開的 GIT repository
需要先把 git repository 設定為公開

接著編寫 .travis.yml, 而部署過程會用到的帳號、密碼這些較敏感內容, 例如 ssh key, access token
travis.org 會要求使用 travis cli 進行打包加密

travis cli tools

這邊我使用別人包裝好的 docker 去完成動作

Docker-travis-cli
https://hub.docker.com/r/skandyla/travis-cli/

當然~ 你也可以自行安裝在本機
(因為這個 工具 並不會一直使用, 比較類似一次性工具所以我選擇用 docker 處理, 比較不會把自己環境搞亂~~~)
https://github.com/travis-ci/travis.rb#readme

.
.

  • 在目標的專案目錄下, 啟用 travis cli 的 docker container

docker run -it --rm -v $(pwd):/project --entrypoint=/bin/sh skandyla/travis-cli

🐳 記得變更 docker 啟動指令裡的 -v(volume), 好讓 docker container 能連結到本機檔案

生成 github access token & travis 登入

travis cli 需要使用到 github 權限; 生成 github access token

https://github.com/settings/tokens > Personal access tokens

所需權限為…
read:org, repo:status, repo_deployment, user:email, write:repo_hook

🤬記得勾選正確, 不然 travis login 會無法登入; 而且回應一個奇怪的錯誤訊息…

.
.
上述動作會拿到一串 token

取得 github access token 後; 回到 travis cli docker container 內使用上述 token 進行登入

travis login --org --github-token xxxxxxxxxxxxxxxxx

登入成功後, 查看登入者

travis whoami

加密 rsync 要用的 ssh private key

使用 rsync 需要 ssh key 登入對象 server
但是為了安全性考量不能直接把 private key 放上 github 或是 travis

所以需要將 ssh private key 透過 travis cli 加密, 避免 private key 直接曝光

🤯 因為 travis ci 在進行部署時是全自動的, 所以在 ssh 指令進行時… 是不會讓操作人員輸入密碼的; 因此需要透過上面的方式讓 ssh key 登入正常

(如何產生 ssh key:
https://www.digitalocean.com/community/tutorials/how-to-set-up-ssh-keys–2)

.
.

在 travis cli docker container 內…
假設 private key 檔名為 id_rsa, 並於同層目錄執行下面指令將其加密

travis encrypt-file id_rsa --add

完成後, 會自動將加密檔存到同層目錄下並將解密指令寫至 .travis.yml

e.g.

openssl aes-256-cbc -K $encrypted_0a6446eb3ae3_key -iv $encrypted_0a6446eb3ae3_iv -in super_secret.txt.enc -out super_secret.txt -d

參考樣式: travis.yml example/demo

.
.

另外~ travis cli 也會生成一個 binary 加密檔在同目錄下
e.g.
https://github.com/cscolabear/travis-ci-auto-deploy/blob/master/.travis/digitalocean_travis_rsa.enc

官方參考文件 ref.
https://docs.travis-ci.com/user/encrypting-files/

🤔因為我不喜歡檔案散落, 所以特別把 .enc 移進 .travis 目錄下
有類似需求記得修改 .travis.yml 裡的相關路徑與檔名

travis 環境變數

在上述的加密過程中, 工具將會自動設定兩組環境變數; 如下圖

在這裡~ 我們也可以設定待使用的變數或是不想曝光的參數

  • HOST_IP: 網站 server IP
  • PUBLISH_PATH: 網站檔案上傳的路徑, e.g. /var/www/travis-ci-auto-deploy
  • SSH_USER: ssh 和 rsync 要使用的帳號名稱
    (ps: 你需要在網站 server 上建立一個可以 ssh key 登入的帳號)

當然, 你也可以依照自己的需求, 任意加入變數使用~
或使用 travis 預設的變數
https://docs.travis-ci.com/user/environment-variables/#default-environment-variables

加入 slack 回報

因為 travis 是全自動建置, 可以透過多種方式告知管理員建置狀態~

slack access token 也需要透過 travis cli 加密

slack travis ci APP 頁面上有詳細教學

e.g.

travis encrypt "workxplay:43xxxxxZg" --add notifications.slack

ref.
詳細請參考 slack + travis 自動回報設定
https://axdlog.com/zh/2018/setting-up-slack-build-notification-in-travis-ci-for-github-project/

Cron Jobs

免費版的 travis 有基本的排程執行功能~ 雖然功能相對陽春但也夠用了

travis 專案 > settings

travis.yml example/demo

最後~ .travis.yml 可能長的像這樣

github:
https://github.com/cscolabear/travis-ci-auto-deploy/blob/master/.travis.yml

因為 wordpress quote 有點問題, 推薦看上面的 github 連結 🤣

language: php
php:
  - '7.2'

branches:
  only:
    - master

addons:
  ssh_known_hosts:
    - '$HOST_IP'

before_install:
  - openssl aes-256-cbc -K $encrypted_12c8071d2874_key -iv $encrypted_12c8071d2874_iv -in .travis/digitalocean_travis_rsa.enc -out ~/.ssh/id_rsa -d
  - chmod 600 ~/.ssh/id_rsa
  - echo -e 'Host ${HOST_IP}\n\tStrictHostKeyChecking no\n' >> ~/.ssh/config
  - php download_and_save.php

script:
  - rsync -az --delete --exclude='.*' ./* ${SSH_USER}@${HOST_IP}:${PUBLISH_PATH}

notifications:
  slack:
    secure: ZYfxxxxxxxEOnNbg=

travis build

透過 travis 頁面上和 .yml 的設定, 只要 git master branch 更新
travis 將自動 trigger build

e.g.

沒有任何錯誤的情況下
網站部署就完成, 資料內容也一並更新 🤗
https://cola.workxplay.net/travis-ci-auto-deploy/

最後~
希望大家好好善用 travis ci 的功能, 但是不要濫用他喔 🙇‍♂️

備註 & 障礙排除

Q. 什麼是 CI/CD

A. 英文全名 Continuous Integration / Continuous Delivery
簡單來說就是自動化更新程式、部署
除了大家常認知的把程式上傳到 server, 中間還可以安插其它工作, 例如執行測試或像本篇文章一樣, 偷跑爬蟲 😓

Q. 什麼是 travis ci

A. 線上 CI/CD(Continuous Integration and Deployment)服務
可以綁定 github 或是其它 GIT 服務, 利用 docker 進行指定的流程及部署功能
可以省去自行建置 CI/CD 服務的麻煩

Q. 什麼是 rsync

A. 使用更好的效率比對來源與目地端的檔案差異再進類傳輸~
https://zh.wikipedia.org/wiki/Rsync

比直接使用 FTP 上傳檔案更有效率

Q. travis 沒反應, 不會自動編輯

A. 可能是 .travis.yml 格式或內容有誤, 可以試著用 travis cli 做 yml 驗證

travis lint

Q. SSH 或 rsync 指令出現 ECDSA 等訊息?

ssh 登入、連線時會出現下面訊息(遠端金鑰確認)該怎麼辦?

e.g.

The authenticity of host '123.123.123 (123.123.123)' can't be established.
ECDSA key fingerprint is 87:a8:8a:50:9c:a9:87:3e:c5:17:6d:b0:f1:28:7e:d3.
Are you sure you want to continue connecting (yes/no)? 

A. 讓 travis ci docker container 認識遠端機器就可以了

  • 關掉檢查

echo -e \'Host ${HOST_IP}\n\tStrictHostKeyChecking no\n\' >> ~/.ssh/config
  • 加入 know host
    https://docs.travis-ci.com/user/ssh-known-hosts/

ref.
同步發表於~

玩工大學
https://uni.workxplay.net/t/github-travis-org/39

可樂

View Comments

  • 謝謝你的文章,非常感激!我在 travis 環境變數卡了非常久,最後看到你這篇才意識到我登入.com 的 travis 但一直是在用 .org 的 travis,難怪變數加密後存不過去。都快瘋掉,再次感謝!

Recent Posts

plain PHP 搭配 Slack 進行錯誤追蹤、回報(Error Tracking、Error Handling)

錯誤追蹤、回報非常重要,看到的錯誤才知道怎麼修。現今 PHP 流行的 Laravel 有很好的 Error Tracking, Error Handling。但 plain PHP 怎麼辦呢? 在 production 為了安全考量會設定…

4 years ago

Drone CI/CD 配合 Github 使用 Rsync 進行 Deploy

jenkins、circleci、travis 或 Gitlab CI 皆為目前暫知名的 CI/CD 服務,各自缺點也不言而喻...過於肥大、收費略高(?)、速度不夠快執問題...此時使用 go language 開發的 Drone 就出現啦,完全 docker 容器化的運行方式讓整個 CI…

4 years ago

Nginx brotli 設定

網頁壓縮技術中 gzip 很好用,deflate 己經過時,但你聽過 brotli 嗎? 有著比 gzip 更好、更快的壓縮效率。看起來利大於弊有什麼不用他的理由嗎?簡單從優、缺點來看 brotli!到底 brotli 布羅特利是什麼、如何設定呢。 目前大多的 web server…

4 years ago

本機使用 Docker 容器內 PHP (wrapper/expose PHP)

為什麼要讓本機使用 Docker 內 PHP? 情境... docker 容器內用的是 PHP 7.4 但你的開發本機還在跑 PHP 5.6 或是更舊,因為 dockerize 的關係會將所有相關環境都轉移到…

4 years ago

為什麼你需要密碼管理工具

為什麼你需要密碼管理工具現代人一天下來需要輸入多少組密碼,工作與生活己經和密碼密不可分! 除了足夠全安的密碼,密碼記錄、儲存的方式又足夠安全嗎?密碼管理工具可以帶來什麼幫助呢? 為什麼你需要密碼管理工具 資安問題!!大多人說著沒做壞事不怕被偷資料、監聽。嚴重曝露出現代人的基本科技素養的低落和無知 🤯 密碼的使用無所不在!! 行動裝置的普及,APP 、手機遊戲、銀行帳戶所有和生活相關的東西都需要密碼!!facebook, line 只要打開 APP 也會輸入密碼只是他是自動輸入、一般情況不可視 (auth token) 一般人最常發生的密碼資安問題…

4 years ago

簡單使用 Mysql Partition 優化查詢

mysql 資料表分區 mysql table partition 從架構上調整 mysql 的查詢效率。mysql DB 的優化可以簡單也能複雜,除了調整設定值。也可以透過水平分割(Horizontal Partitioning)、垂直分割(Vertical Partitioning) 分庫或分表將資料分散儲存減少資料搜尋、group by 時的效能消耗。拆開批次處理,理論上效率都會變好,本文就水平分割的…

4 years ago