From c15714113231513782a5253c0c0e4d4290a9d6f2 Mon Sep 17 00:00:00 2001 From: Tom Ward Date: Fri, 10 Nov 2023 15:36:44 +0000 Subject: [PATCH] feat: CI build process for grafana --- .github/workflows/grafana.yml | 112 ++++++++++++++++++++++++++++++++++ grafana/docker-compose.yml | 12 ++++ grafana/dotenv-sample | 1 + grafana/justfile | 28 +++++++++ 4 files changed, 153 insertions(+) create mode 100644 .github/workflows/grafana.yml create mode 100644 grafana/docker-compose.yml create mode 100644 grafana/dotenv-sample create mode 100644 grafana/justfile diff --git a/.github/workflows/grafana.yml b/.github/workflows/grafana.yml new file mode 100644 index 00000000..14818a07 --- /dev/null +++ b/.github/workflows/grafana.yml @@ -0,0 +1,112 @@ +--- +name: Grafana deployment + +env: + IMAGE_NAME: grafana + PUBLIC_IMAGE_NAME: ghcr.io/ebmdatalab/grafana + REGISTRY: ghcr.io + SSH_AUTH_SOCK: /tmp/agent.sock + +on: + push: + +jobs: + lint-dockerfile: + runs-on: ubuntu-latest + + steps: + - uses: actions/checkout@v4 + - uses: hadolint/hadolint-action@54c9adbab1582c2ef04b2016b760714a4bfde3cf # v3.1.0 + with: + dockerfile: grafana/Dockerfile + + docker-test-and-build: + runs-on: ubuntu-latest + + steps: + - uses: actions/checkout@v4 + - uses: "opensafely-core/setup-action@v1" + with: + install-just: true + + - name: Build docker image + run: | + just grafana/build + + - name: Run smoke test + run: | + just grafana/serve + sleep 10 + just grafana/smoke-test || { docker logs grafana-grafana_1; exit 1; } + + - name: Save docker image + run: | + docker save grafana | gzip > /tmp/grafana.tar.gz + + - name: Upload docker image + uses: actions/upload-artifact@v3 + with: + name: grafana-image + path: /tmp/grafana.tar.gz + + required-checks: + if: always() + + needs: + - docker-test-and-build + - lint-dockerfile + + runs-on: Ubuntu-latest + + steps: + - name: Decide whether the needed jobs succeeded or failed + uses: re-actors/alls-green@05ac9388f0aebcb5727afa17fcccfecd6f8ec5fe # v1.2.2 + with: + jobs: ${{ toJSON(needs) }} + + deploy: + needs: [required-checks] + + runs-on: ubuntu-latest + + permissions: + contents: read + packages: write + + if: github.ref == 'refs/heads/main' + + concurrency: deploy-production + + steps: + - uses: actions/checkout@v4 + - uses: "opensafely-core/setup-action@v1" + with: + install-just: true + + - name: Download docker image + uses: actions/download-artifact@v3 + with: + name: grafana-image + path: /tmp/image + + - name: Import docker image + run: gunzip -c /tmp/image/grafana.tar.gz | docker load + + - name: Test image we imported from previous job works + run: | + SKIP_BUILD=1 just grafana/serve + sleep 10 + just grafana/smoke-test || { docker logs grafana-grafana_1; exit 1; } + + - name: Publish image + run: | + echo ${{ secrets.GITHUB_TOKEN }} | docker login "$REGISTRY" -u ${{ github.actor }} --password-stdin + docker tag "$IMAGE_NAME" "$PUBLIC_IMAGE_NAME":latest + docker push "$PUBLIC_IMAGE_NAME":latest + + - name: Deploy image + run: | + ssh-agent -a "$SSH_AUTH_SOCK" > /dev/null + ssh-add - <<< "${{ secrets.DOKKU3_DEPLOY_SSH_KEY }}" + SHA=$(docker inspect --format='{{index .RepoDigests 0}}' "$PUBLIC_IMAGE_NAME":latest) + ssh -o "UserKnownHostsFile=/dev/null" -o "StrictHostKeyChecking=no" dokku@dokku3.ebmdatalab.net git:from-image grafana "$SHA" diff --git a/grafana/docker-compose.yml b/grafana/docker-compose.yml new file mode 100644 index 00000000..d178f1d5 --- /dev/null +++ b/grafana/docker-compose.yml @@ -0,0 +1,12 @@ +services: + grafana: + # use Dockerfile so that version matches production + build: + dockerfile: Dockerfile + ports: + - 3000:3000 + volumes: + - grafana:/var/lib/grafana + +volumes: + grafana: diff --git a/grafana/dotenv-sample b/grafana/dotenv-sample new file mode 100644 index 00000000..c628fc7d --- /dev/null +++ b/grafana/dotenv-sample @@ -0,0 +1 @@ +# This file intentionally blank diff --git a/grafana/justfile b/grafana/justfile new file mode 100644 index 00000000..ce74e892 --- /dev/null +++ b/grafana/justfile @@ -0,0 +1,28 @@ + +build: + #!/usr/bin/env bash + set -euo pipefail + + test -z "${SKIP_BUILD:-}" || { echo "SKIP_BUILD set"; exit 0; } + + # ensure env file exists + test -f .env || cp dotenv-sample .env + + # set build args for prod builds + export BUILD_DATE=$(date -u +'%y-%m-%dT%H:%M:%SZ') + export GITREF=$(git rev-parse --short HEAD) + + # build the thing + docker compose build grafana + +serve: + # Do a basic test with built-in sqlitedb + # this should use the Dockerfile version, or this test is pointless + docker compose up grafana -d + +# run a basic functional smoke test against a running server +smoke-test host="http://127.0.0.1:3000/login": + #!/bin/bash + set -eu + curl -I {{ host }} -s --compressed --fail --retry 20 --retry-delay 1 --retry-all-errors +