Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 23 additions & 0 deletions .github/actions/generate-build-matrix/action.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
name: 'Generate Build Matrix'
description: 'Generates a dynamic build matrix for the cmake-build workflow'
inputs:
user-input:
description: 'The user-provided build combinations from a workflow_dispatch event'
required: false
comment-body:
description: 'The body of the issue comment that triggered the workflow'
required: false
outputs:
matrix:
description: 'The generated build matrix in JSON format'
value: ${{ steps.generate.outputs.matrix }}
runs:
using: 'composite'
steps:
- id: generate
run: python ${{ github.action_path }}/generate_matrix.py
shell: bash
env:
USER_INPUT: ${{ inputs.user-input }}
COMMENT_BODY: ${{ inputs.comment-body }}
GITHUB_EVENT_NAME: ${{ github.event_name }}
53 changes: 53 additions & 0 deletions .github/actions/generate-build-matrix/generate_matrix.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
import json
import os
import re

def main():
all_combinations = [
"gcc/none", "gcc/asan", "gcc/tsan", "gcc/valgrind",
"clang/none", "clang/asan", "clang/tsan", "clang/valgrind"
]
default_excluded = ["clang/none", "clang/valgrind"]

user_input = os.getenv("USER_INPUT", "")
comment_body = os.getenv("COMMENT_BODY", "")
event_name = os.getenv("GITHUB_EVENT_NAME")

input_str = ""
if event_name == "workflow_dispatch":
input_str = user_input
elif event_name == "issue_comment":
match = re.match(r"^@phlexbot build\s*(.*)", comment_body)
if match:
input_str = match.group(1)

tokens = [token for token in re.split(r"[\s,]+", input_str) if token]

if not tokens:
final_combinations = [combo for combo in all_combinations if combo not in default_excluded]
else:
is_additive = any(token == "all" or token.startswith("+") or token.startswith("-") for token in tokens)

if is_additive:
base_set = set(all_combinations if "all" in tokens else [combo for combo in all_combinations if combo not in default_excluded])

for token in tokens:
if token.startswith("+"):
base_set.add(token[1:])
elif token.startswith("-"):
base_set.discard(token[1:])
final_combinations = list(base_set)
else:
final_combinations = tokens

matrix = {"include": []}
for combo in sorted(list(set(final_combinations))):
compiler, sanitizer = combo.split("/")
matrix["include"].append({"compiler": compiler, "sanitizer": sanitizer})

json_matrix = json.dumps(matrix)
with open(os.environ["GITHUB_OUTPUT"], "a") as f:
print(f"matrix={json_matrix}", file=f)

if __name__ == "__main__":
main()
66 changes: 64 additions & 2 deletions .github/workflows/cmake-build.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -9,13 +9,26 @@ on:
push:
branches: [ main, develop ]
workflow_dispatch:
inputs:
build-combinations:
description: |
A space- or comma-separated list of build combinations to run.
Syntax examples:
- `gcc/asan clang/tsan` (run only these two)
- `all` (run all combinations)
- `all -clang/none -clang/valgrind` (run all except specified)
- `+clang/none +clang/valgrind` (run default matrix plus specified)
Default (if empty): Run all except clang/none and clang/valgrind.
required: false
default: ''

permissions:
contents: read
pull-requests: read

env:
BUILD_TYPE: Release
CICOLOR_FORCE: 1

jobs:
pre-check:
Expand All @@ -27,10 +40,13 @@ jobs:
permissions:
contents: read
packages: read

outputs:
is_act: ${{ steps.detect_act.outputs.is_act }}
should_run: ${{ steps.check.outputs.triggered }}
pr_details: ${{ steps.pr.outputs.result }}
sha: ${{ steps.pr.outputs.sha || github.sha }}
repo: ${{ steps.pr.outputs.repo || github.repository }}

steps:
- name: Check trigger condition
Expand Down Expand Up @@ -79,6 +95,7 @@ jobs:
packages: read
outputs:
has_changes: ${{ steps.filter.outputs.matched }}
matrix: ${{ steps.generate.outputs.matrix }}

steps:
- name: Check out source code
Expand Down Expand Up @@ -108,6 +125,12 @@ jobs:
echo "::endgroup::"
fi

- id: generate
uses: ./phlex-src/.github/actions/generate-build-matrix
with:
user-input: ${{ github.event.inputs.build-combinations }}
comment-body: ${{ github.event.comment.body }}

build:
needs: [pre-check, detect-changes]
if: >
Expand All @@ -123,6 +146,9 @@ jobs:
github.event.comment.author_association == 'OWNER'
)
runs-on: ubuntu-24.04
strategy:
fail-fast: false
matrix: ${{ fromJSON(needs.generate-matrix.outputs.matrix) }}

container:
image: ghcr.io/framework-r-d/phlex-ci:latest
Expand All @@ -137,19 +163,55 @@ jobs:
- name: Setup build environment
uses: Framework-R-D/phlex/.github/actions/setup-build-env@main

- name: Announce CMake configuration
run: echo "➡️ Configuring CMake..."

- name: Configure CMake
id: configure
uses: Framework-R-D/phlex/.github/actions/configure-cmake@main
with:
build-type: ${{ env.BUILD_TYPE }}
cpp-compiler: ${{ matrix.compiler == 'gcc' && 'g++' || 'clang++' }}
extra-options: |
${{ matrix.sanitizer == 'asan' && '-DPHLEX_ENABLE_ASAN=ON' || '' }}
${{ matrix.sanitizer == 'tsan' && '-DPHLEX_ENABLE_TSAN=ON' || '' }}

- name: Build
id: build
uses: Framework-R-D/phlex/.github/actions/build-cmake@main

- name: Test
- name: Run tests
if: matrix.sanitizer != 'valgrind'
run: |
. /entrypoint.sh
cd $GITHUB_WORKSPACE/phlex-build
ctest -j $(nproc)

echo "➡️ Running tests..."
echo "::group::Running ctest"
if ctest --progress --output-on-failure -j $(nproc); then
echo "::endgroup::"
echo "✅ All tests passed."
else
echo "::endgroup::"
echo "::error:: Some tests failed."
exit 1
fi

- name: Run Valgrind tests
if: matrix.sanitizer == 'valgrind'
run: |
. /entrypoint.sh
cd $GITHUB_WORKSPACE/phlex-build

echo "➡️ Running Valgrind tests..."
echo "::group::Running ctest -T memcheck"
if ctest -T memcheck; then
echo "::endgroup::"
echo "✅ Valgrind tests passed."
else
echo "::endgroup::"
echo "⚠️ Valgrind tests failed, but the workflow will continue."
fi

cmake-build-skipped:
needs: [pre-check, detect-changes]
Expand Down
Loading