gossとGitHub Actionsでインフラを自動テストした

こんにちは! DevOpsが好きな小山です.
今回はCDSLのインフラにテストを入れた話です.

なぜテストをするのか

テストといえばソフトウェアテストを想像するかと思います.テストコードを書いてユニットテストや結合テスト,E2Eテストに聞き覚えのある方もいると思います.

インフラにおいても正常に動作しているかや構築が上手くできているかを確かめるためにテストが行われます.テストフレームワークで有名なものは,Serverspecです.そのほかにもTestinfraやGossがあります.

今回はテストフレームワークとしてGossを使用してGitHub Actionsを組み合わせたオンプレミス環境のインフラへの自動テストを実装しました.

GitHub Actions

GitHub ActionsはGitHubが公式で提供しているワークフローツール(CI/CD環境)です.事前に定義したルールに基づいてビルドやテスト,デプロイといったタスクを実行できます.今回はこの仕組みを使って自動テストを定期的に実行します.

Features • GitHub Actions

GitHub Actionsをオンプレミス(研究室)の環境で実行するために,GitHub Actions Self Hosted Runnerを使いました.これは,GitHubが提供する環境ではなく,オンプレミスの環境でGitHub Actionsのタスクを実行するためのソフトウェアです.インストール方法は以前にQiitaの記事で書きました.

今回はGitHub ActionsをBootstrap(テスト実行の起点)として使い,gossの呼び出しとSlack通知を行っています.

Goss

Gossはインフラを対象としたテストフレームワークです.YAML形式で設定を記述すると,それに基づいてテストを行います.設定の生成ができることやServerspecに比べ高速な点が優れているそうです.

aelsabbahy/goss: Quick and Easy server testing/validation

自動テストの実装

gossの設定ファイルは必要な項目を手動で記述しました.これの自動生成が今後の課題です.以下はgoss.yamlの一部です.

http:
  # kibana
  http://192.168.100.10/:
    status: 200
    allow-insecure: true
    timeout: 1000
    skip: false
dns:
  elasticsearch-edge.a910.tak-cslab.org:
    resolvable: true
    addrs:
      - 192.168.100.10
      - 192.168.100.11
    server: 192.168.100.6
    timeout: 500
command:
  proxy-ping:
    exit-status: 0
    exec: "ping -c 5 -t 10 192.168.100.3"
    skip: false
    timeout: 5000

GitHub Actionsでは,3時間おきの定期実行とPushされたタイミングでの実行を設定してあります.gossはSelf Hosted Runnerを起動しているVMにあらかじめインストールしました.

Actionsではgossの呼び出しと失敗時のSlack通知を行っています.失敗したときだけ通知する方法で悩みましたが,technote-space/workflow-conclusion-action@v2を使うことで実現できました.

name: Main Test

on:
  push:
    branches:
      - main
  schedule:
    - cron:  '00 */3 * * *'

jobs:
  goss-test:
    runs-on: self-hosted
    steps:
      - uses: actions/checkout@v2
      # - name: Install Goss
      #   uses: e1himself/goss-installation-action@v1.0.3
      #   with:
      #     version: 'v0.3.14'
      - name: Run Command
        run: |
          goss validate --format documentation
    outputs:
      job_status: ${{ job.status }}
  slack-notify:
    if: always()
    runs-on: Ubuntu-20.04
    needs: goss-test
    steps:
      - uses: technote-space/workflow-conclusion-action@v2
      - uses: rtCamp/action-slack-notify@v2
        env:
          SLACK_WEBHOOK: ${{ secrets.SLACK_BOT_TOKEN }}
          SLACK_USERNAME: "Infra Auto Test"
          SLACK_ICON_EMOJI: ":fox_face:"
          SLACK_COLOR: danger
          SLACK_TITLE: "Infra Test Failed"
          SLACK_MESSAGE: "Please check infra test status https://github.com/cdsl-research/infra-test/actions :fire:"
          SLACK_FOOTER: "Powered by GitHub Actions"
          MSG_MINIMAL: true
        if: env.WORKFLOW_CONCLUSION == 'failure'

テストが失敗するとSlackに次の通知が流れます.これでいつ何が起きたのかを検出できるようになりますね.

Slackにテスト失敗が通知された図

今後はテスト項目の追加や自動生成,自動復旧を実現していきたいと考えています.まだテストの追加と修正を繰返しています.

テストの実行履歴

CDSLではこうしたインフラの自動テストやDevOps,監視といったキーワードにも取り組んでいます.興味のある学生はぜひ研究室見学やカジュアル面談を申し込んでもらえると嬉しいです.というか僕が主に喜びます.

Leave a Reply