Skip to content

feat: Refactored building action service tests and added handling of … #292

feat: Refactored building action service tests and added handling of …

feat: Refactored building action service tests and added handling of … #292

name: Build services
on:
push:
paths:
- "go.mod"
- ".github/workflows/**"
- "build/**"
- "database/**"
- "pkg/**"
- "internal/**"
- "cmd/**"
# https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/control-the-concurrency-of-workflows-and-jobs#example-only-cancel-in-progress-jobs-on-specific-branches
# https://stackoverflow.com/questions/66335225/how-to-cancel-previous-runs-in-the-pr-when-you-push-new-commitsupdate-the-curre
concurrency:
group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }}
cancel-in-progress: true
jobs:
check-test-names:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: Detect tests not matching naming pattern
id: matching
# https://unix.stackexchange.com/questions/330660/preventing-grep-from-causing-premature-termination-of-bash-e-script
run: |
grep -rh 'func Test' --include *_test.go > all_tests.txt
sed -i 's/func //g' all_tests.txt
cat all_tests.txt | cut -d'(' -f1 > test_names.txt
grep -v TestMain test_names.txt > test_without_main.txt
grep -vE '^Test(Unit|IT|)_' test_without_main.txt > not_matching.txt || [[ $? == 1 ]]
FAILURES=$(wc -l < not_matching.txt)
if [[ ${FAILURES} -ne 0 ]]; then
echo 'failed=true' >> $GITHUB_OUTPUT
fi
- name: Fail if some do not match
if: ${{ steps.matching.outputs.failed == 'true' }}
# https://docs.github.com/en/actions/writing-workflows/choosing-what-your-workflow-does/workflow-commands-for-github-actions#example-setting-an-error-message
run: |
echo "::error ::Detected at least one test not matching the naming convention!"
exit 1
tests:
runs-on: ubuntu-latest
needs: [check-test-names]
steps:
- uses: actions/checkout@v4
- name: Setup Go
uses: actions/setup-go@v5
with:
go-version: "1.23.2"
- name: Run tests with coverage
run: go test -run='^TestUnit_.*' ./... -coverpkg=./... -race -covermode=atomic -coverprofile=coverage.out
- name: Upload coverage to Codecov
uses: codecov/codecov-action@v5
with:
fail_ci_if_error: true
files: ./coverage.out
token: ${{ secrets.CODECOV_TOKEN }}
it-tests:
runs-on: ubuntu-latest
needs: [check-test-names]
services:
postgres:
image: postgres:15
env:
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
POSTGRES_DB: postgres
ports:
- 5432:5432
options: >-
--health-cmd pg_isready
--health-interval 10s
--health-timeout 5s
--health-retries 5
steps:
- uses: actions/checkout@v4
- name: Setup Go
uses: actions/setup-go@v5
with:
go-version: "1.23.2"
- name: Install migrate tool
run: go install -tags 'postgres' github.com/golang-migrate/migrate/v4/cmd/migrate@latest
- name: Setup galactic-sovereign database
run: |
psql \
postgresql://postgres@localhost \
-v admin_password=$ADMIN_PASSWORD \
-v manager_password=$MANAGER_PASSWORD \
-v user_password=$USER_PASSWORD \
-f galactic-sovereign/db_user_create.sql
psql \
postgresql://postgres@localhost \
-f galactic-sovereign/db_create.sql
working-directory: ./database
env:
PGPASSWORD: postgres
ADMIN_PASSWORD: admin_password
MANAGER_PASSWORD: manager_password
USER_PASSWORD: user_password
- name: Migrate schema up
run: |
migrate \
-path galactic-sovereign/migrations \
-database postgresql://galactic_sovereign_admin@localhost/db_galactic_sovereign?sslmode=disable \
up
working-directory: ./database
env:
PGPASSWORD: admin_password
- name: Run tests with coverage
run: go test -run='^TestIT_.*' ./... -coverpkg=./... -race -covermode=atomic -coverprofile=coverage.out
- name: Upload coverage to Codecov
uses: codecov/codecov-action@v5
with:
fail_ci_if_error: true
files: ./coverage.out
token: ${{ secrets.CODECOV_TOKEN }}
extract-service-tag:
runs-on: ubuntu-latest
# https://docs.github.com/en/actions/using-jobs/defining-outputs-for-jobs
outputs:
version: ${{ steps.service-version.outputs.tag }}
steps:
- uses: actions/checkout@v4
- name: Extract git commit hash
id: service-version
# https://stackoverflow.com/questions/58886293/getting-current-branch-and-commit-hash-in-github-action
run: echo "tag=$(git rev-parse --short $GITHUB_SHA)" >> $GITHUB_OUTPUT
build-and-push-docker-image:
runs-on: ubuntu-latest
needs: [extract-service-tag, tests, it-tests]
steps:
- uses: actions/checkout@v4
- name: Login to Docker Hub
uses: docker/login-action@v3
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
# https://docs.github.com/en/actions/publishing-packages/publishing-docker-images#publishing-images-to-docker-hub
- name: Build and push
uses: docker/build-push-action@v6
with:
context: .
file: ./build/galactic-sovereign-service/Dockerfile
build-args: GIT_COMMIT_HASH=${{ needs.extract-service-tag.outputs.version }}
push: true
tags: totocorpsoftwareinc/galactic-sovereign-service:${{ needs.extract-service-tag.outputs.version }}
e2e-tests:
runs-on: ubuntu-latest
needs: [build-and-push-docker-image, extract-service-tag]
services:
postgres:
image: postgres:15
env:
POSTGRES_USER: postgres
POSTGRES_PASSWORD: postgres
POSTGRES_DB: postgres
ports:
- 5432:5432
options: >-
--health-cmd pg_isready
--health-interval 10s
--health-timeout 5s
--health-retries 5
steps:
- uses: actions/checkout@v4
- name: Setup Go
uses: actions/setup-go@v5
with:
go-version: "1.23.2"
- name: Install migrate tool
run: go install -tags 'postgres' github.com/golang-migrate/migrate/v4/cmd/migrate@latest
- name: Setup galactic-sovereign database
run: |
psql \
postgresql://postgres@localhost \
-v admin_password=$ADMIN_PASSWORD \
-v manager_password=$MANAGER_PASSWORD \
-v user_password=$USER_PASSWORD \
-f galactic-sovereign/db_user_create.sql
psql \
postgresql://postgres@localhost \
-f galactic-sovereign/db_create.sql
working-directory: ./database
env:
PGPASSWORD: postgres
ADMIN_PASSWORD: admin_password
MANAGER_PASSWORD: manager_password
USER_PASSWORD: user_password
- name: Migrate schema up
run: |
migrate \
-path galactic-sovereign/migrations \
-database postgresql://galactic_sovereign_admin@localhost/db_galactic_sovereign?sslmode=disable \
up
working-directory: ./database
env:
PGPASSWORD: admin_password
- name: Login to Docker Hub
uses: docker/login-action@v3
with:
username: ${{ secrets.DOCKERHUB_USERNAME }}
password: ${{ secrets.DOCKERHUB_TOKEN }}
- name: Pull latest docker image
run: |
docker pull totocorpsoftwareinc/galactic-sovereign-service:${{ needs.extract-service-tag.outputs.version }}
- name: Test docker image
# https://superuser.com/questions/272265/getting-curl-to-output-http-status-code
# https://stackoverflow.com/questions/24254064/how-to-get-curl-to-output-only-http-response-body-json-and-no-other-headers-et
# https://docs.github.com/en/actions/use-cases-and-examples/using-containerized-services/about-service-containers#running-jobs-on-the-runner-machine
run: |
docker run \
-d \
--name galactic-sovereign-service-test \
-e ENV_SERVER_PORT=$PORT \
-e ENV_DATABASE_PASSWORD=$DATABASE_PASSWORD \
-p 1234:1234 \
totocorpsoftwareinc/galactic-sovereign-service:${{ needs.extract-service-tag.outputs.version }}
echo "status_code=$(curl -s -o /dev/null -w %{http_code} localhost:1234/v1/galactic-sovereign/universes)" >> $GITHUB_OUTPUT
echo "response_body=$(curl -s localhost:1234/v1/galactic-sovereign/universes)" >> $GITHUB_OUTPUT
docker stop galactic-sovereign-service-test
id: test-results
env:
PORT: 1234
DATABASE_PASSWORD: manager_password
- name: Print test results
run: |
echo ${{ steps.test-results.outputs.status_code }}
echo ${{ steps.test-results.outputs.response_body }}
- name: Verify status code
run: |
if [[ ${{ steps.test-results.outputs.status_code }} != '200' ]]; then
echo "::error ::Expected http status code to be 200 but it was ${{ steps.test-results.outputs.status_code }}!"
exit 1
fi
- name: Verify response body
# https://stackoverflow.com/questions/58862864/github-actions-ci-conditional-regex
# https://stackoverflow.com/questions/4542732/how-do-i-negate-a-test-with-regular-expressions-in-a-bash-script
run: |
if ! [[ '${{ steps.test-results.outputs.response_body }}' =~ ^\{\"requestId\":\"[0-9a-f-]+\",\"status\":\"SUCCESS\",\"details\":\[[^]]+\]\}$ ]]; then
echo "::error ::Expected http response to match expected syntax but it did not: ${{ steps.test-results.outputs.response_body }}!"
exit 1
fi
update-deployment:
runs-on: ubuntu-latest
needs: [extract-service-tag, e2e-tests]
if: github.ref == 'refs/heads/master'
steps:
- uses: actions/checkout@v4
with:
repository: "Knoblauchpilze/ec2-deployment"
# https://stackoverflow.com/questions/64374179/how-to-push-to-another-repository-in-github-actions
token: ${{ secrets.DEPLOYMENT_TOKEN }}
- name: Update service tag
run: |
echo "${{ needs.extract-service-tag.outputs.version }}" > ./build/galactic-sovereign-service/version.txt
- name: "Commit changes"
run: |
git pull
git config --global user.name 'totocorpbot'
git config --global user.email '[email protected]'
git commit -am "infra: Bumped galactic-sovereign-service version to ${{ needs.extract-service-tag.outputs.version }}"
git push