LoginSignup
32
18

More than 3 years have passed since last update.

GitHub ActionsでCI/CD環境を学びながら構築する

Last updated at Posted at 2020-05-23

はじめに

GitHub Actionsを使ってCI/CD環境を構築します。
今回の目標はFirebaseGatsbyで作った静的なWebサイトを自動的にビルド、デプロイする環境の構築です。

GitHub Actionsとは

GitHubのリポジトリにCI(継続的インテグレーション)とCD(継続的デプロイメント)の機能を直接作ることができる機能。
CIについては公式ドキュメントで丁寧に解説されています。
継続的インテグレーションについて

GitHub Actionsのことば

では早速CI/CD環境を構築していきたいのですが、私はCI/CDツールに関するリテラシーがまだまだ低いので、GitHub Actionsで登場する概念を学びつつ進めましょう。

ワークフローとは

GitHub Actionsで言うワークフローとは、任意のプロジェクトをビルドしたり、テストしたり、デプロイしたり…という様々な作業のまとまりです。
実際にはプロジェクトのルートに.github/workflowsというディレクトリを作り、その中に*.ymlファイルを作り、このファイルに具体的な処理を記述します。*.ymlファイルが1つのワークフローとして定義され、プロジェクトで複数のワークフローを定義できます。

ジョブとは

ワークフローの中で実行される処理のひとまとまりをジョブと呼んでいます。ジョブはワークフローに複数定義することができ、それぞれのジョブは並行して処理されます。
また、ジョブはそれを実行するマシンを指定できます。(例えばMacとかWindowsとか)

ステップとは

ジョブの中で実行される一連のタスク。ワークフローを構成する様々なタスクの最小単位という感じ。
npm installを実行する、npm run buildを実行する、くらい具体的なタスクです。

アクションとは

ステップとして実行されるタスクの中で再利用可能なコードの単位をアクションと呼びます。
例えば『Firbaseにデプロイする』という一連のタスクを再利用可能な形にしているもののことです。

なんとなくGitHub Actionsの概念を掴んできたところで、次は実際のワークフローを定義している*.ymlファイルを見てみます。結局は見たほうがわかりますしね。

GitHub Action for Firebaseを使ってみる

GitHubのMarketplaceには様々なアクションが用意されています。今回はその中からGitHub Action for Firebaseを使ってワークフローを作ります。

ちなみにこのときのプロジェクトはこんな構成です。

root
├── .github
│   └── workflows
│       └── firebase.yml
├── node_modules
├── public
│   └── ビルドされたファイルはここにできる
├── src
│   └── ソースファイルたくさん
├── .firebaserc
├── .gitignore
├── package.json
├── yarn.lock
├── その他諸々

このプロジェクトに、GitHub Action for FirebaseのExampleを参考にワークフローを作成します。
↓これはExampleを私の環境で使うために少し手を加えたワークフローです。

.github/workflows/firebase.yml
name: Build and Deploy
on:
  push:
    branches:
      - master

jobs:
  build:
    name: Build
    runs-on: ubuntu-latest
    steps:
      - name: Checkout Repo
        uses: actions/checkout@master
      - name: Install Dependencies
        run: npm install
      - name: Build
        run: npm run build
      - name: Archive Production Artifact
        uses: actions/upload-artifact@master
        with:
          name: public
          path: public
  deploy:
    name: Deploy
    needs: build
    runs-on: ubuntu-latest
    steps:
      - name: Checkout Repo
        uses: actions/checkout@master
      - name: Download Artifact
        uses: actions/download-artifact@master
        with:
          name: public
          path: public
      - name: Deploy to Firebase
        uses: w9jds/firebase-action@master
        with:
          args: deploy
        env:
          FIREBASE_TOKEN: ${{ secrets.FIREBASE_TOKEN }}

私は今回CI/CDツール初体験ですが、こうしてコードで見るとこのワークフローが何をしようとしているのか、なんとなくわかりますね。
それではこのワークフローをちゃんと理解するため、順番にコードを読んでいきましょう。

.github/workflows/firebase.yml
name: Build and Deploy
on:
  push:
    branches:
      - master
# 以下略

この部分はワークフローの名前と、このワークフローをトリガーするイベントが記述されています。
今回の例だと、masterブランチに新しいコードがプッシュされた時にトリガーされます。なんてわかりやすいんでしょう。

続いてBuildジョブの部分を読んでみます。

Buildジョブ

jobs:
  build:
    name: Build
    runs-on: ubuntu-latest
    steps:
      - name: Checkout Repo
        uses: actions/checkout@master
      - name: Install Dependencies
        run: npm install
      - name: Build
        run: npm run build
      - name: Archive Production Artifact
        uses: actions/upload-artifact@master
        with:
          name: public
          path: public

Buildジョブがどのように定義されているか順に読んでいきます。

jobs.build

buildはこのジョブを一意に特定するためのIDです。英数字、-_のみ使えます。

jobs.build.name

このジョブの名前です。読んだまんまですね。たぶんこの値はそんなに重要じゃないのかなーと思います。

jobs.build.runs-on

このジョブを実行するマシンを定義します。
ここでMacやWindowsも選べますが、今回はUbuntuの最新版にしています。これも読んだまんまという感じです。

jobs.build.steps.name

ここからステップを定義していきます。まずは名前です。はい、読んだまんまですね。

jobs.build.steps.uses

ここでアクションを使うことができます。
uses: actions/checkout@masterというのは、GitHubのactions/checkoutというパブリックリポジトリのアクションのmasterブランチのコードを使わせていただく、という意味です。
このアクションでは、チェックアウトするリポジトリや、Gitの参照を指定できるのですが、今回は何も指定していません。デフォルトで、このワークフローのあるリポジトリのmasterブランチにチェックアウトしてくれます。

jobs.build.steps.run

シェルコマンドを実行できます。
シェルを明示的に指定することもできますが、デフォルトではこのジョブを実行しているマシンのシェルで実行するので、今回は明示していません。

成果物をジョブ間でビルドしたファイルを受け渡す

Buildジョブではもちろんビルドするわけですが、この後デプロイするためにはこのビルドしたアプリを次のDeployジョブに受け渡す必要があります。そのためのアクションがactions/upload-artifactactions/download-artifactです。また、このビルドして生成されたファイルを成果物と呼びます。
npm run buildで成果物を生成し、これをactions/upload-artifactでGitHub上のストレージに保存します(この成果物は90日間保存されます)。

Buildジョブはこれで完了です。続いてDeployジョブも読んでみましょう。

Deployジョブ

jobs:

  # ここにBuildジョブ

  deploy:
    name: Deploy
    needs: build
    runs-on: ubuntu-latest
    steps:
      - name: Checkout Repo
        uses: actions/checkout@master
      - name: Download Artifact
        uses: actions/download-artifact@master
        with:
          name: public
          path: public
      - name: Deploy to Firebase
        uses: w9jds/firebase-action@master
        with:
          args: deploy
        env:
          FIREBASE_TOKEN: ${{ secrets.FIREBASE_TOKEN }}

Buildジョブとは違う部分だけ見ていきましょう。

jobs.deploy.needs

ジョブが複数ある場合、それらは基本的に並行して処理されますが、ジョブが処理される順序を設定することもできます。
jobs.deploy.needsにジョブIDを設定すると、そのジョブが完了するまで待機させることができます。このワークフローでは、DeployジョブはBuildジョブが完了してから実行するようにしています。

w9jds/firebase-action

このアクションのjobs.deploy.steps.with.argsにfirebase CLIのコマンドを引数として渡すことで、fiebase-toolsを使えるようになります。
ただし、Firebase CLIをCIツールで使うためには認証に必要なトークンを取得し、jobs.deploy.steps.envFIREBASE_TOKENにわたす必要があります。

Firebase CLIの認証トークンを設定

まずはトークンを取得します。
ローカルのプロジェクトルートでfirebase login:ciを実行すると、ブラウザが起動してログインを促されるのでGoogleアカウントでログインします。

ログインが成功したらシェルにトークンが表示されます。

Waiting for authentication...

✔  Success! Use this token to login on a CI server:

***************************************** // ここにトークン

Example: firebase deploy --token "$FIREBASE_TOKEN"

これでトークンの用意ができました。これをGitHubのリポジトリに設定できる環境変数に設定します。

暗号化された環境変数を使う

GitHubはリポジトリに対して暗号化された環境変数を設定することができます。
リポジトリのSettings > サイドバーのSecrets > New secret > NameValueを入力 > Add secret
という感じで非常に簡単かつ安全にトークンを保存できます。
そしてここで設定した環境変数をsecrets.FIREBASE_TOKENという形で呼び出すことができます。

実行してみる

これでCI/CD環境は構築できたので、早速このワークフローを試してみましょう。適当にコミットしてmasterブランチにプッシュします。
するとリポジトリのActionsタブから、実行されたワークフローのログを確認できます。
02.png
見事全てのジョブが完了しました:grin:

参考

GitHub Actionsのワークフロー構文
成果物を使用してワークフローデータを永続化する
GitHub Action for Firebase
Firebase CLI リファレンス #CI システムで CLI を使用する
暗号化されたシークレットの作成と保存

32
18
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
32
18