Netlify と Circle CIでのReact SPAのCI / CD

いい方法が思いつかなくて、Netlifyチームに「ぶっちゃけどうやるのがいいの?」って聞いてみた。

今回のサンプル

特に意味はないですが、Gatsbyあんまり触ってないのであえて使ってみます。

$ npx gatsby new netlify-cli-test
$ cd netlify-cli-test
$ git init
$ git add ./
$ git commit -m "init"
$ git remote add origin <YOUR_GITHUB_REPO>
$ git push origin master

GitHubのリポジトリとの関連付けまでこれですみました。

Netlifyと連携する

とりあえずサイトをそのままデプロイしてみましょう。

ちなみにGitのリポジトリが空だと怒られるので、pushしておきましょう。

ビルドのコマンドなどいろいろ聞かれますが、デフォルトのまま進めればOKです。ブランチはmasterにしておきましょう。

Netlifyのデプロイが終わって、サイトが表示されればStep1クリアです。

Circle CI用のジョブ(リント)を用意する

続いてユニットテストなどをまわすためにCircle CIもつなぎます。

$ mkdir .circleci
$ vim .circleci/config.yml
version: 2
jobs:
  build:
    working_directory: ~/repo
    docker:
      - image: circleci/node:8.11-browsers
    steps:
      - checkout
      - restore_cache:
          keys:
            - test-{{ .Branch }}-{{ checksum "yarn.lock" }}
            # fallback
            - test-{{ checksum "yarn.lock" }}
      - run: yarn install
      - save_cache:
          paths:
            - node_modules
          key: test-{{ .Branch }}-{{ checksum "yarn.lock" }}
      - run: yarn run lint

CI上で確認するタスクが必要なので、今回はESLintでのリントをいれてみましょう。prettrier入ってるから要らんやろという声もありそうですが、テストコード書くより楽なので無視します。

$ yarn add -D eslint
$ ./node_modules/.bin/eslint --init

# package.jsonに`npm run lint`を追加
$ vim package.json

...
    "format": "prettier --write \"src/**/*.js\"",
    "test": "echo \"Write tests! -> https://gatsby.app/unit-testing\"",
    "lint": "eslint src/"
  },
  "devDependencies": {

あとはyarn run lintで動くことを確認しましょう。エラーが出る場合は、オフにするか手で修正するかで通るようにします。

ここまでの作業をcommitして、gitでpushしておきます。Circle CIと連携できればビルドが走るでしょう。

やりたいこと

  • テスト系のジョブはCircle CIでやりたい
  • ビルド系のジョブはNetlifyでやりたい

ビルド系はNetlifyのログがいろいろ見れて便利、ただテスト系はCircle CIでやった方が融通が効きやすいので両方使いたいのです。

このわがままを達成させていきます。

Netlifyでビルドwebhookを用意する

Netlifyではwebhookを利用してビルドを実行することができます。Settings > Build & deploy > Continuous deployment > Build hooksからwebhookのURLを発行しましょう。

以下のようにPOSTしてやることでビルドが実行されます。

$ curl -X POST -d {} https://api.netlify.com/build_hooks/XXXXXX

Netlifyの自動ビルドを動かなくする

続いてNetlifyが実行する自動ビルドを止めます。

Settings > Build & deploy > Continuous deployment > Deploy contextsを以下のように変更しましょう。

ポイントは「存在しないブランチをproduction扱いにする」「Pull Requestでのビルドも停止する」というところです。もっとも、「Pull RequestのレビュービルドはCircle CIと並列で構わない」というケースであれば、Deploy previewsはデフォルトのままでよいかもしれません。

Circle CIからビルドさせる

最後にCircle CIからビルドを開始するようにします。masterブランチのみビルドさせたいので、最後にcurlさせています。

version: 2
jobs:
  build:
    working_directory: ~/repo
    docker:
      - image: circleci/node:8.11-browsers
    steps:
<中略>
      - run: yarn run lint
      - deploy:
          command: |
           if [ "${CIRCLE_BRANCH}" == "master" ]; then
            curl -X POST -d {} https://api.netlify.com/build_hooks/XXXXXXXXXX
           fi

これで「テスト系はCircle CIで実施」と「テスト系が問題なければNetlifyでビルドを実行する」の2つを実現できるようになります。

Comment