Skip to content

Refactor CI workflow to update published app artifact download action #63

Refactor CI workflow to update published app artifact download action

Refactor CI workflow to update published app artifact download action #63

Workflow file for this run

# name of the workflow. Link to the documentation - https://docs.github.com/en/actions/reference/workflow-syntax-for-github-actions#name
name: CI
# running on push to main and develop branches or on pull reuqests or on manual trigger
on:
# manual trigger
workflow_dispatch:
inputs:
ssh_debug_enabled:
type: boolean
description: 'Run the build/test with ssh debugging enabled (https://github.com/marketplace/actions/debugging-with-tmate)'
required: false
default: false
debug_deployment:
type: boolean
description: 'Run the pipeline with debug deployment enabled'
required: false
default: false
# runnnig on push to main and develop branches
push:
branches:
- main
- develop
paths-ignore:
- '**/README.md'
- '.devcontainer/**'
# running on pull requests to main and develop branches
pull_request:
branches:
- main
- develop
paths-ignore:
- '**/README.md'
- '.devcontainer/**'
# defining global environment variables for all jobs
env:
# define runner indexes for tests splitting and parallel execution
total-runners: 4
# defining GitHub registry for docker images
REGISTRY: ghcr.io
# github.repository as <account>/<repo>
IMAGE_NAME: ${{ github.repository }}
jobs:
build:
runs-on: ${{ matrix.os }}
name: Build ${{ matrix.os }}
permissions:
actions: read
contents: read
packages: write
id-token: write
security-events: write
strategy:
matrix:
# os: [ubuntu-latest, windows-latest, macos-latest]
os: [ubuntu-latest]
language: [csharp]
steps:
- name: Checkout code
uses: actions/[email protected]
- name: Setup .NET
uses: actions/[email protected]
with:
dotnet-version: '6.0.x'
- name: Cache NuGet packages
uses: actions/[email protected]
with:
path: ~/.nuget/packages
key: ${{ runner.os }}-nuget-${{ hashFiles('**/*.csproj', '**/global.json') }}
restore-keys: |
${{ runner.os }}-nuget-
- name: Restore dependencies
run: dotnet restore RazorPagesMovie.csproj
- name: Build App project
run: dotnet build RazorPagesMovie.csproj --configuration Release --no-restore
- name: Set runtime
id: set-runtime
run: echo "RUNTIME=${{ matrix.os == 'ubuntu-latest' && 'linux-arm64' || matrix.os == 'windows-latest' && 'win-x64' || 'osx-x64' }}" >> $GITHUB_ENV
- name: Publish
run: dotnet publish RazorPagesMovie.csproj --configuration Release --output ./publish --self-contained --runtime ${{ env.RUNTIME }}
- name: Upload published app
uses: actions/upload-artifact@v3
with:
name: razor-linux-arm64
path: publish/
test:
runs-on: ${{ matrix.os }}
needs:
- build
- runner-indexes
permissions:
contents: read # read access to the repository contents
packages: write # write access to the repository packages
id-token: write # write access to the repository id token
strategy:
matrix:
# os: [ubuntu-latest, windows-latest, macos-latest]
os: [ubuntu-latest]
index: ${{ fromJson(needs.runner-indexes.outputs.json) }}
steps:
- name: Checkout code
uses: actions/[email protected]
- name: Setup .NET
uses: actions/[email protected]
with:
dotnet-version: '6.0.x'
- name: Cache NuGet packages
uses: actions/[email protected]
with:
path: ~/.nuget/packages
key: ${{ runner.os }}-nuget-${{ hashFiles('**/*.csproj', '**/global.json') }}
restore-keys: |
${{ runner.os }}-nuget-
- name: Setup tmate session
uses: mxschmitt/action-tmate@v3
if: ${{ github.event_name == 'workflow_dispatch' && inputs.ssh_debug_enabled }}
- name: Split Tests
id: split-test
uses: chaosaffe/[email protected]
with:
glob: RazorPagesMovie.Tests/**/*Tests.cs
split-total: ${{ env.total-runners }}
split-index: ${{ matrix.index }}
line-count: true
- name: Restore dependencies
run: dotnet restore RazorPagesMovie.Tests/RazorPagesMovie.Tests.csproj
- name: Convert Test File Path to Fully Qualified Name
id: convert-path
run: |
test_suite="${{ steps.split-test.outputs.test-suite }}"
fully_qualified_name=$(echo $test_suite | sed 's/\//./g' | sed 's/.cs//g')
echo "fully_qualified_name=$fully_qualified_name" >> $GITHUB_ENV
- run: 'echo "This runner will execute the following tests: ${{ steps.split-test.outputs.test-suite }}."'
- run: |
dotnet test RazorPagesMovie.Tests/RazorPagesMovie.Tests.csproj \
--filter "FullyQualifiedName~${{ env.fully_qualified_name }}" \
--logger "console;verbosity=detailed" \
--logger "trx;LogFileName=./testresults-${{ matrix.index }}-testresults-${{ matrix.os }}-${{ github.run_id }}-${{ github.run_attempt }}.trx" \
--results-directory ./testresults
- name: Upload test results
if: always()
uses: actions/[email protected]
with:
name: testresults-${{ github.run_id }}-split-${{ matrix.index }}
path: ./testresults
if-no-files-found: warn
compression-level: 6
publish-test-results:
needs: test
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/[email protected]
- name: List Artifacts
id: list-artifacts
run: |
curl -s -u ${{ github.actor }}:${{ secrets.GITHUB_TOKEN }} \
-H 'Accept: application/vnd.github.v3+json' \
https://api.github.com/repos/octodemo/dotnet-razor-pages-movie/actions/runs/${{ github.run_id }}/artifacts > artifacts.json
- name: Download Artifacts
run: |
mkdir -p test_results
for url in $(jq -r '.artifacts[] | select(.name | startswith("testresults-")) | .archive_download_url' artifacts.json); do
artifact_name=$(echo $url | awk -F/ '{print $NF}' | awk -F? '{print $1}')
curl -s -u ${{ github.actor }}:${{ secrets.GITHUB_TOKEN }} -L -o test_results/testresults.zip $url
unzip -o test_results/testresults.zip -d test_results
rm test_results/testresults.zip
done
- name: Publish Test Results
uses: dorny/[email protected]
if: always()
with:
reporter: dotnet-trx
name: xUnit Test Results
path: test_results/**/*.trx
build-and-publish-docker-image: # job to build the docker image and publish it to the GitHub Container Registry
runs-on: ubuntu-latest # using the latest ubuntu runner
outputs:
image_tag: ghcr.io/${{ github.repository }}:${{ github.run_number }} # output the image tag to be used in the build-and-publish-docker-image job
needs: [build, test] # depend on the build job to get the published app artifact
if: github.ref == 'refs/heads/main' # run this job only when the branch is main branch and not on pull requests or other branches - https://docs.github.com/en/actions/reference/context-and-expression-syntax-for-github-actions#github-context
# permissions for write acces to the packages and id-token and push access to the repository to create the container registry token
permissions:
packages: write
id-token: write
contents: write
steps:
- name: Checkout repository
uses: actions/checkout@v3
- uses: actions/download-artifact@v3 # download the published app artifact from the build job
with:
name: razor-linux-arm64
path: publish/
# build the docker image using the Dockerfile in the root of the repository
# and tag it with the current run number from the github action workflow run
- name: Log in to the GH Container Registry
uses: docker/login-action@f054a8b539a109f9f41c372932f1ae047eff08c9 # using the docker login action from the github marketplace - github.com/marketplace/actions/docker-login
with:
registry: ${{ env.REGISTRY }} # using the registry environment variable
username: ${{ github.actor }} # using the github.actor context
password: ${{ secrets.GITHUB_TOKEN }} # using the GITHUB_TOKEN secret
- name: Build and push Docker image
id: build_image
uses: docker/build-push-action@v4 # using the docker build and push action from the github marketplace - github.com/marketplace/actions/build-and-push-docker-images
with:
context: . # using the current directory as the context
push: true # push the docker image to the registry
tags: |
ghcr.io/${{ github.repository }}:${{ github.run_number }}
ghcr.io/${{ github.repository }}:latest
cache-from: type=registry,ref=ghcr.io/${{ github.repository }}:latest # use the docker layer caching to speed up the docker image build process
cache-to: type=inline
runner-indexes: # job to generate the runner indexes for the unit-parallel-tests job
runs-on: ubuntu-latest
name: Generate runner indexes
outputs:
json: ${{ steps.generate-index-list.outputs.json }} # output the json with the runner indexes
steps:
- id: generate-index-list # generate the runner indexes and save them to the json file
run: |
MAX_INDEX=$((${{ env.total-runners }}-1)) # calculate the max index
INDEX_LIST=$(seq 0 ${MAX_INDEX}) # generate the list of indexes
INDEX_JSON=$(jq --null-input --compact-output '. |= [inputs]' <<< ${INDEX_LIST}) # convert the list to the json
echo "json=${INDEX_JSON}" >> $GITHUB_OUTPUT # save the json to the GITHUB_OUTPUT environment variable