From 42191affbb0ca4f4aef950ac74dbd73a8f9fd9f3 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Wed, 23 Sep 2026 10:18:23 +0200 Subject: [PATCH 01/26] Clone Regression --- .github/workflows/CI_build_and_test.yml | 79 ++++++++++++++++--------- 1 file changed, 51 insertions(+), 28 deletions(-) diff --git a/.github/workflows/CI_build_and_test.yml b/.github/workflows/CI_build_and_test.yml index 39174cd246e..afdba103373 100644 --- a/.github/workflows/CI_build_and_test.yml +++ b/.github/workflows/CI_build_and_test.yml @@ -77,7 +77,7 @@ jobs: echo "additionnal-cmake-flags : ${{ inputs.additionnal-cmake-flags }}" echo "builder-os : ${{ inputs.builder-os }}" - + build: strategy: fail-fast: false @@ -120,7 +120,7 @@ jobs: echo "WARNING: cannot setup git config" fi - - name: Clone SOFA and CI + - name: Clone SOFA, CI and Regression id: clone shell: bash run: | @@ -134,7 +134,7 @@ jobs: ## Clone sofa and merge origin master echo "Cloning SOFA at commit $GITHUB_WORKFLOW_SHA" if [ -d $WORKSPACE/sofa ]; then - rm -rf $WORKSPACE/sofa + rm -rf $WORKSPACE/sofa fi SRC_DIR=$(pwd)/sofa echo "SRC_DIR=$SRC_DIR" >> $GITHUB_ENV @@ -144,8 +144,8 @@ jobs: git clone -b ${{ inputs.sofa-branch-name }} --single-branch https://www.github.com/sofa-framework/sofa cd sofa git remote add pr ${{ inputs.pr-owner-url }} - git fetch pr - + git fetch pr + if [ "${{ inputs.pr-commit-sha }}" == "HEAD" ]; then git merge ${{ inputs.pr-branch-name }} else @@ -153,19 +153,19 @@ jobs: fi else echo "This is not a PR: checking out sha ${{ inputs.sofa-commit-sha }} from branch ${{ inputs.sofa-branch-name }}" - git clone -b ${{ inputs.sofa-branch-name }} --single-branch https://www.github.com/sofa-framework/sofa + git clone -b ${{ inputs.sofa-branch-name }} --single-branch https://www.github.com/sofa-framework/sofa cd sofa git checkout ${{ inputs.sofa-commit-sha }} fi cd $WORKSPACE - + ## Clone CI and use ci-depends-on structure ci_branch=${{ inputs.sofa-branch-name }} ci_repo_url="https://www.github.com/sofa-framework/ci" - - # check if ci has a ci-depends-on + + # check if ci has a ci-depends-on ci_ci_depends_on=$(echo "${{ inputs.ci-depends-on }}" | jq .ci) if [ -n "${{ inputs.ci-depends-on }}" ] && [ "$ci_ci_depends_on" != "null" ]; then echo "ci-depends-on for ci repository detected." @@ -176,7 +176,7 @@ jobs: echo "Cloning CI from remote ${ci_repo_url}, selecting branch ${ci_branch}" - + if [ -d $WORKSPACE/ci ]; then rm -rf $WORKSPACE/ci fi @@ -187,6 +187,33 @@ jobs: cd $WORKSPACE + ## Clone Regression and use ci-depends-on structure + regression_branch=${{ inputs.sofa-branch-name }} + regression_repo_url="https://www.github.com/sofa-framework/Regression" + + + # check if ci has a ci-depends-on + regression_ci_depends_on=$(echo "${{ inputs.ci-depends-on }}" | jq .Regression) + if [ -n "${{ inputs.ci-depends-on }}" ] && [ "$regression_ci_depends_on" != "null" ]; then + echo "ci-depends-on for Regression repository detected." + regression_repo_url=$(echo "${{ inputs.ci-depends-on }}" | jq .Regression.repo_url) + regression_branch=$(echo "${{ inputs.ci-depends-on }}" | jq .Regression.branch_name) + fi + echo "REGRESSION_BRANCH=$regression_branch" >> $GITHUB_ENV + + + echo "Cloning Regression from remote ${regression_repo_url}, selecting branch ${regression_branch}" + + if [ -d $WORKSPACE/Regression ]; then + rm -rf $WORKSPACE/Regression + fi + REGRESSION_DIR=$WORKSPACE/Regression + echo "REGRESSION_DIR=$REGRESSION_DIR" >> $GITHUB_ENV + + git clone -b ${regression_branch//\"} --single-branch ${regression_repo_url//\"} + + cd $WORKSPACE + ## Setup build folder if [ "${{ inputs.force-full-build }}" == "true" ] && [ -d $WORKSPACE/build ]; then rm -rf $WORKSPACE/build @@ -211,7 +238,7 @@ jobs: fi ## Cleaning old tests results of they exists - if [ -d "${{ env.BUILD_DIR }}/tests_results/" ]; then + if [ -d "${{ env.BUILD_DIR }}/tests_results/" ]; then echo "Cleaning old test results folder." rm -rf "${{ env.BUILD_DIR }}/tests_results/" fi @@ -267,7 +294,7 @@ jobs: echo "" | tee -a "${{ env.LOG_DIR }}/cmake-output.txt" echo "Configuration:" | tee -a "${{ env.LOG_DIR }}/cmake-output.txt" echo " - NODE_NAME = $NODE_NAME" | tee -a "${{ env.LOG_DIR }}/cmake-output.txt" - echo " - BUILD_TYPE = $BUILD_TYPE" | tee -a "${{ env.LOG_DIR }}/cmake-output.txt" + echo " - BUILD_TYPE = $BUILD_TYPE" | tee -a "${{ env.LOG_DIR }}/cmake-output.txt" echo " - CONFIG = $CONFIG" | tee -a "${{ env.LOG_DIR }}/cmake-output.txt" echo " - PYTHON_VERSION = ${{ inputs.python-version }}" | tee -a "${{ env.LOG_DIR }}/cmake-output.txt" echo " - PRESET = ${{ inputs.preset }}" | tee -a "${{ env.LOG_DIR }}/cmake-output.txt" @@ -283,9 +310,9 @@ jobs: default_tag=${{ inputs.sofa-branch-name }} else default_tag=master - fi + fi - echo "${DOCKERHUB_TOKEN}" | docker login -u sofaframework --password-stdin + echo "${DOCKERHUB_TOKEN}" | docker login -u sofaframework --password-stdin echo "Pulling Docker image sofaframework/sofabuilder_${builder_type}:${CI_BRANCH} ..." docker pull --quiet sofaframework/sofabuilder_${builder_type}:${CI_BRANCH} || true @@ -316,13 +343,13 @@ jobs: docker run --rm --env XDG_CACHE_HOME --env GH_TOKEN="$GH_TOKEN" -v $BUILDER_CACHE_DIR:/cache\ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "env; echo \"$GH_TOKEN\" > gh auth login --with-token; gh auth setup-git; gh auth status; cd /workspace; ccache -M 5; /bin/bash $DOCKER_CI_DIR/scripts/configure-and-build.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ $DOCKER_LOG_DIR \"${NODE_NAME}\" \"${BUILD_TYPE}\" \"${CONFIG}\" \"${{ inputs.python-version }}\" \"${{ inputs.preset }}\" \"${{ inputs.generate-binaries }}\" \"${CMAKE_OPTIONS}\"" + /bin/bash -c "env; echo \"$GH_TOKEN\" > gh auth login --with-token; gh auth setup-git; gh auth status; cd /workspace; ccache -M 5; /bin/bash $DOCKER_CI_DIR/scripts/configure-and-build.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ $DOCKER_LOG_DIR \"${NODE_NAME}\" \"${BUILD_TYPE}\" \"${CONFIG}\" \"${{ inputs.python-version }}\" \"${{ inputs.preset }}\" \"${{ inputs.generate-binaries }}\" \"${CMAKE_OPTIONS}\"" else echo "Launching configuration and build" bash ${CI_DIR}/scripts/configure-and-build.sh "${BUILD_DIR}" "${SRC_DIR}" "${CI_DIR}/scripts/" "${{ env.LOG_DIR }}" "${NODE_NAME}" "${BUILD_TYPE}" "${CONFIG}" "${{ inputs.python-version }}" "${{ inputs.preset }}" "${{ inputs.generate-binaries }}" "${CMAKE_OPTIONS}" fi - + - name: Unit tests id: unit-tests-step @@ -337,7 +364,7 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} UNIT" + /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} UNIT" else echo "Launching unit test suite." @@ -361,7 +388,7 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} SCENE" + /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} SCENE" else echo "Launching scene test suite." @@ -385,7 +412,7 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} REGRESSION" + /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} REGRESSION" else echo "Launching regression test suite" @@ -404,8 +431,8 @@ jobs: name: binaries_${{ env.BUILDER_OS }} path: | ${{ env.BUILD_DIR }}/SOFA_v* - - + + - name: Publish build logs id: publish-build-logs if: always() @@ -448,7 +475,7 @@ jobs: else echo "✅ Build OK." fi - + if [[ "${{ inputs.generate-binaries }}" == "false" ]]; then if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -maxdepth 1 -type f)" != "" ]]; then echo "❌ Tests have resulted in : " @@ -459,10 +486,10 @@ jobs: echo "#---------------Quick Logs---------------#" echo "#----------------------------------------#" for testType in 'unit' 'scene' 'regression'; - do + do for errorType in 'errors' 'crashes' 'failures'; do - if [ -f "${{ env.BUILD_DIR }}/tests_results/${testType}-tests_${errorType}" ]; then + if [ -f "${{ env.BUILD_DIR }}/tests_results/${testType}-tests_${errorType}" ]; then capitalized="$(echo "${testType:0:1}" | tr '[:lower:]' '[:upper:]')${testType:1}" echo "" echo -e "${bold}${capitalized} ${errorType}:${normal}" @@ -486,7 +513,3 @@ jobs: echo "" fi fi - - - - From 31cff32537ba4b73ed47cad0bb85b5b913b1229e Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Wed, 23 Sep 2026 11:13:00 +0200 Subject: [PATCH 02/26] Try new python based scripts on ubuntu and macos --- .github/workflows/CI_build_and_test.yml | 23 ++++++++++++++--------- 1 file changed, 14 insertions(+), 9 deletions(-) diff --git a/.github/workflows/CI_build_and_test.yml b/.github/workflows/CI_build_and_test.yml index afdba103373..7102676b1b1 100644 --- a/.github/workflows/CI_build_and_test.yml +++ b/.github/workflows/CI_build_and_test.yml @@ -330,11 +330,13 @@ jobs: DOCKER_SRC_DIR="/workspace/$(realpath --relative-to=$WORKSPACE $SRC_DIR)" DOCKER_BUILD_DIR="/workspace/$(realpath --relative-to=$WORKSPACE $BUILD_DIR)" DOCKER_CI_DIR="/workspace/$(realpath --relative-to=$WORKSPACE $CI_DIR)" + DOCKER_REGRESSION_DIR="/workspace/$(realpath --relative-to=$WORKSPACE $REGRESSION_DIR)" DOCKER_LOG_DIR="/workspace/$(realpath --relative-to=$WORKSPACE ${{ env.LOG_DIR }})" echo "DOCKER_SRC_DIR=$DOCKER_SRC_DIR" >> $GITHUB_ENV echo "DOCKER_BUILD_DIR=$DOCKER_BUILD_DIR" >> $GITHUB_ENV echo "DOCKER_CI_DIR=$DOCKER_CI_DIR" >> $GITHUB_ENV + echo "DOCKER_REGRESSION_DIR=$DOCKER_REGRESSION_DIR" >> $GITHUB_ENV echo "DOCKER_LOG_DIR=$DOCKER_LOG_DIR" >> $GITHUB_ENV export XDG_CACHE_HOME="/cache" @@ -364,14 +366,15 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} UNIT" + /bin/bash -c "env ; cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"${RESULTS_DIR}/unit\" -j ${VM_MAX_PARALLEL_TESTS}" else echo "Launching unit test suite." - bash ${CI_DIR}/scripts/test.sh "${BUILD_DIR}" "${SRC_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" "UNIT" + . ${CI_DIR}/scripts/setup-test-env.sh "${BUILD_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" + ${VM_PYTHON3_EXECUTABLE} ${CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir "${BUILD_DIR}" --results-dir "${RESULTS_DIR}/unit" -j ${VM_MAX_PARALLEL_TESTS} fi - if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -maxdepth 1 -type f)" == *"unit-tests_"* ]]; then + if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/unit" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then exit 1 fi @@ -388,14 +391,15 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} SCENE" + /bin/bash -c "env ; cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${DOCKER_SRC_DIR}" --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"${RESULTS_DIR}/scene\" -j ${VM_MAX_PARALLEL_TESTS}" else echo "Launching scene test suite." - bash ${CI_DIR}/scripts/test.sh "${BUILD_DIR}" "${SRC_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" "SCENE" + . ${CI_DIR}/scripts/setup-test-env.sh "${BUILD_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" + ${VM_PYTHON3_EXECUTABLE} ${CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${SRC_DIR}" --build-dir "${BUILD_DIR}" --results-dir "${RESULTS_DIR}/scene" -j ${VM_MAX_PARALLEL_TESTS} fi - if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -maxdepth 1 -type f)" == *"scene-tests_"* ]]; then + if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/scene" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then exit 1 fi @@ -412,14 +416,15 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} REGRESSION" + /bin/bash -c "export REGRESSION_DIR="$DOCKER_REGRESSION_DIR"; env ; cd /workspace;. ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${DOCKER_SRC_DIR}/examples" --input "${DOCKER_SRC_DIR}/applications" --input "${DOCKER_BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" -j ${VM_MAX_PARALLEL_TESTS} --legacy-regression" else echo "Launching regression test suite" - bash ${CI_DIR}/scripts/test.sh "${BUILD_DIR}" "${SRC_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" "REGRESSION" + . ${CI_DIR}/scripts/setup-test-env.sh "${BUILD_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" + ${VM_PYTHON3_EXECUTABLE} ${REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${SRC_DIR}/examples" --input "${SRC_DIR}/applications" --input "${BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" -j ${VM_MAX_PARALLEL_TESTS} --legacy-regression fi - if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -maxdepth 1 -type f)" == *"regression-tests_"* ]]; then + if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/regression" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then exit 1 fi From 6466b3bc256122d286d43340a323690bdf5df289 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Wed, 23 Sep 2026 11:13:54 +0200 Subject: [PATCH 03/26] TO REVERT, this enables to test my script --- .../workflows/CI_trigger_build_and_tests.yml | 28 +++++++++---------- 1 file changed, 14 insertions(+), 14 deletions(-) diff --git a/.github/workflows/CI_trigger_build_and_tests.yml b/.github/workflows/CI_trigger_build_and_tests.yml index da2efb038be..388ac0ad045 100644 --- a/.github/workflows/CI_trigger_build_and_tests.yml +++ b/.github/workflows/CI_trigger_build_and_tests.yml @@ -28,10 +28,10 @@ on: preset: type: choice description: Which preset to use for compilation - options: + options: - standard - supported-plugins - - full + - full - standard-dev - supported-plugins-dev - full-dev @@ -39,16 +39,16 @@ on: builder-os: type: choice description: On which OS run the binaries generation - options: + options: - '["sh-ubuntu_gcc_release"]' - '["sh-macos_clang_release"]' - '["sh-ubuntu_gcc_release","sh-macos_clang_release"]' default: '["sh-ubuntu_gcc_release","sh-macos_clang_release"]' - + # PR-related build (open, labels, push) pull_request: types: [opened, synchronize] - + # CI for dashboard master push: branches: @@ -79,7 +79,7 @@ jobs: PR_BRANCH_NAME: ${{ steps.export-vars.outputs.PR_BRANCH_NAME }} PR_COMMIT_SHA: ${{ steps.export-vars.outputs.PR_COMMIT_SHA }} BUILDER_OS: ${{ steps.export-vars.outputs.BUILDER_OS }} - + steps: - name: Default values of environment variables run: | @@ -97,7 +97,7 @@ jobs: echo "PR_BRANCH_NAME=" >> $GITHUB_ENV # PR_BRANCH_NAME: "" echo "PR_COMMIT_SHA=HEAD" >> $GITHUB_ENV # PR_COMMIT_SHA: "HEAD" echo 'BUILDER_OS=["sh-ubuntu_gcc_release"]' >> $GITHUB_ENV # BUILDER_OS: ["sh-ubuntu_gcc_release"] - + - name: Run on dispatch if: ${{ github.event_name == 'workflow_dispatch' }} run: | @@ -122,7 +122,7 @@ jobs: fi fi echo "Python version $PYTHON is valid." - + # Save all information in environment variables echo "SOFA_BRANCH_NAME=${{ github.event.inputs.branch }}" >> $GITHUB_ENV echo "SOFA_COMMIT_SHA=HEAD" >> $GITHUB_ENV @@ -170,11 +170,11 @@ jobs: PR_COMMIT_SHA: ${{ github.event.pull_request.head.sha }} run: | echo "This step runs only when a PR is opened or synchronized." - + # Trigger the Build action # Warning ! This script also changes ENV variables python ci/scripts/checkPRInfoBeforeBuild.py - + - name: Export environment variables as outputs id: export-vars run: | @@ -184,7 +184,7 @@ jobs: echo "Branch name should be either master or any release branch (e.g., v25.06)" exit 1 fi - + echo "SOFA_BRANCH_NAME=${SOFA_BRANCH_NAME}" >> $GITHUB_OUTPUT echo "SOFA_COMMIT_SHA=${SOFA_COMMIT_SHA}" >> $GITHUB_OUTPUT echo "PRESET=${PRESET}" >> $GITHUB_OUTPUT @@ -192,8 +192,8 @@ jobs: echo "CI_DEPENDS_ON=${CI_DEPENDS_ON}" >> $GITHUB_OUTPUT echo "WITH_ALL_TESTS=${WITH_ALL_TESTS}" >> $GITHUB_OUTPUT echo "FORCE_FULL_BUILD=${FORCE_FULL_BUILD}" >> $GITHUB_OUTPUT - echo "EXTERNAL_PLUGINS=${EXTERNAL_PLUGINS}" >> $GITHUB_OUTPUT - echo "ADDITIONNAL_CMAKE_FLAGS=${ADDITIONNAL_CMAKE_FLAGS}" >> $GITHUB_OUTPUT + echo "EXTERNAL_PLUGINS=${EXTERNAL_PLUGINS}" >> $GITHUB_OUTPUT + echo "ADDITIONNAL_CMAKE_FLAGS=${ADDITIONNAL_CMAKE_FLAGS}" >> $GITHUB_OUTPUT echo "GENERATE_BINARIES=${GENERATE_BINARIES}" >> $GITHUB_OUTPUT echo "PR_OWNER_URL=${PR_OWNER_URL}" >> $GITHUB_OUTPUT echo "PR_BRANCH_NAME=${PR_BRANCH_NAME}" >> $GITHUB_OUTPUT @@ -208,7 +208,7 @@ jobs: build-on: needs: filter_build if: ${{ github.repository_owner == 'sofa-framework' }} - uses: sofa-framework/sofa/.github/workflows/CI_build_and_test.yml@master + uses: bakpaul/sofa/.github/workflows/CI_build_and_test.yml@26_09_update_ci_with_new_test_scripts_and_pixi_based_ci_for_windows with: sofa-branch-name: ${{ needs.filter_build.outputs.SOFA_BRANCH_NAME }} sofa-commit-sha: ${{ needs.filter_build.outputs.SOFA_COMMIT_SHA }} From c15c8e36a5ca7c4db6781905be3415d3e098d984 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Wed, 23 Sep 2026 14:01:58 +0200 Subject: [PATCH 04/26] Add insight for debug --- .github/workflows/CI_build_and_test.yml | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-) diff --git a/.github/workflows/CI_build_and_test.yml b/.github/workflows/CI_build_and_test.yml index 117153d99b0..ca7790663e1 100644 --- a/.github/workflows/CI_build_and_test.yml +++ b/.github/workflows/CI_build_and_test.yml @@ -349,11 +349,12 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "env ; cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"${RESULTS_DIR}/unit\" -j ${VM_MAX_PARALLEL_TESTS}" + /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"${RESULTS_DIR}/unit\" -j ${VM_MAX_PARALLEL_TESTS}" else echo "Launching unit test suite." . ${CI_DIR}/scripts/setup-test-env.sh "${BUILD_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" + env ${VM_PYTHON3_EXECUTABLE} ${CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir "${BUILD_DIR}" --results-dir "${RESULTS_DIR}/unit" -j ${VM_MAX_PARALLEL_TESTS} fi @@ -374,11 +375,12 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "env ; cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${DOCKER_SRC_DIR}" --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"${RESULTS_DIR}/scene\" -j ${VM_MAX_PARALLEL_TESTS}" + /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${DOCKER_SRC_DIR}" --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"${RESULTS_DIR}/scene\" -j ${VM_MAX_PARALLEL_TESTS}" else echo "Launching scene test suite." . ${CI_DIR}/scripts/setup-test-env.sh "${BUILD_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" + env ${VM_PYTHON3_EXECUTABLE} ${CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${SRC_DIR}" --build-dir "${BUILD_DIR}" --results-dir "${RESULTS_DIR}/scene" -j ${VM_MAX_PARALLEL_TESTS} fi @@ -399,11 +401,12 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "export REGRESSION_DIR="$DOCKER_REGRESSION_DIR"; env ; cd /workspace;. ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${DOCKER_SRC_DIR}/examples" --input "${DOCKER_SRC_DIR}/applications" --input "${DOCKER_BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" -j ${VM_MAX_PARALLEL_TESTS} --legacy-regression" + /bin/bash -c "export REGRESSION_DIR="$DOCKER_REGRESSION_DIR"; cd /workspace;. ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${DOCKER_SRC_DIR}/examples" --input "${DOCKER_SRC_DIR}/applications" --input "${DOCKER_BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" -j ${VM_MAX_PARALLEL_TESTS} --legacy-regression" else echo "Launching regression test suite" . ${CI_DIR}/scripts/setup-test-env.sh "${BUILD_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" + env ${VM_PYTHON3_EXECUTABLE} ${REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${SRC_DIR}/examples" --input "${SRC_DIR}/applications" --input "${BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" -j ${VM_MAX_PARALLEL_TESTS} --legacy-regression fi From d22ac9a2d34235ee32e6396dde6f07d9915c1765 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Wed, 23 Sep 2026 14:40:52 +0200 Subject: [PATCH 05/26] Tru pass number threads --- .github/workflows/CI_build_and_test.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/CI_build_and_test.yml b/.github/workflows/CI_build_and_test.yml index ca7790663e1..9177567db57 100644 --- a/.github/workflows/CI_build_and_test.yml +++ b/.github/workflows/CI_build_and_test.yml @@ -401,13 +401,13 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "export REGRESSION_DIR="$DOCKER_REGRESSION_DIR"; cd /workspace;. ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${DOCKER_SRC_DIR}/examples" --input "${DOCKER_SRC_DIR}/applications" --input "${DOCKER_BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" -j ${VM_MAX_PARALLEL_TESTS} --legacy-regression" + /bin/bash -c "export REGRESSION_DIR="$DOCKER_REGRESSION_DIR"; cd /workspace;. ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${DOCKER_SRC_DIR}/examples" --input "${DOCKER_SRC_DIR}/applications" --input "${DOCKER_BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" --legacy-regression --jobs ${VM_MAX_PARALLEL_TESTS} " else echo "Launching regression test suite" . ${CI_DIR}/scripts/setup-test-env.sh "${BUILD_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" env - ${VM_PYTHON3_EXECUTABLE} ${REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${SRC_DIR}/examples" --input "${SRC_DIR}/applications" --input "${BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" -j ${VM_MAX_PARALLEL_TESTS} --legacy-regression + ${VM_PYTHON3_EXECUTABLE} ${REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${SRC_DIR}/examples" --input "${SRC_DIR}/applications" --input "${BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" --legacy-regression -j ${VM_MAX_PARALLEL_TESTS} fi if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/regression" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then From 6995b575d76799f99b5cd94b13bcd47a7fcf1adb Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Wed, 23 Sep 2026 14:46:28 +0200 Subject: [PATCH 06/26] Print command line --- .github/workflows/CI_build_and_test.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/CI_build_and_test.yml b/.github/workflows/CI_build_and_test.yml index 9177567db57..25dc4db2875 100644 --- a/.github/workflows/CI_build_and_test.yml +++ b/.github/workflows/CI_build_and_test.yml @@ -349,7 +349,7 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"${RESULTS_DIR}/unit\" -j ${VM_MAX_PARALLEL_TESTS}" + /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env; echo \"${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir ${DOCKER_BUILD_DIR} --results-dir ${RESULTS_DIR}/unit -j ${VM_MAX_PARALLEL_TESTS}\"" else echo "Launching unit test suite." From e5776af4b54ae59bf7f9043ea6cdbed54e32d322 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Wed, 23 Sep 2026 15:06:55 +0200 Subject: [PATCH 07/26] Bad substitution level --- .github/workflows/CI_build_and_test.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/CI_build_and_test.yml b/.github/workflows/CI_build_and_test.yml index 25dc4db2875..e8f5d92c0f1 100644 --- a/.github/workflows/CI_build_and_test.yml +++ b/.github/workflows/CI_build_and_test.yml @@ -349,7 +349,7 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env; echo \"${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir ${DOCKER_BUILD_DIR} --results-dir ${RESULTS_DIR}/unit -j ${VM_MAX_PARALLEL_TESTS}\"" + /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir ${DOCKER_BUILD_DIR} --results-dir \${RESULTS_DIR}/unit -j \${VM_MAX_PARALLEL_TESTS}" else echo "Launching unit test suite." @@ -375,7 +375,7 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${DOCKER_SRC_DIR}" --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"${RESULTS_DIR}/scene\" -j ${VM_MAX_PARALLEL_TESTS}" + /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${DOCKER_SRC_DIR}" --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"\${RESULTS_DIR}/scene\" -j \${VM_MAX_PARALLEL_TESTS}" else echo "Launching scene test suite." @@ -401,7 +401,7 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "export REGRESSION_DIR="$DOCKER_REGRESSION_DIR"; cd /workspace;. ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${DOCKER_SRC_DIR}/examples" --input "${DOCKER_SRC_DIR}/applications" --input "${DOCKER_BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" --legacy-regression --jobs ${VM_MAX_PARALLEL_TESTS} " + /bin/bash -c "export REGRESSION_DIR="$DOCKER_REGRESSION_DIR"; cd /workspace;. ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${DOCKER_SRC_DIR}/examples" --input "${DOCKER_SRC_DIR}/applications" --input "${DOCKER_BUILD_DIR}/external_directories/fetched" --output-logs-errors "\${RESULTS_DIR}/regression" --legacy-regression --jobs \${VM_MAX_PARALLEL_TESTS} " else echo "Launching regression test suite" From f56409d91ce1cc846392b79760f2b12e1590be0e Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Wed, 23 Sep 2026 17:44:34 +0200 Subject: [PATCH 08/26] Fix summarize results --- .github/workflows/CI_build_and_test.yml | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/.github/workflows/CI_build_and_test.yml b/.github/workflows/CI_build_and_test.yml index e8f5d92c0f1..d13c0fb7697 100644 --- a/.github/workflows/CI_build_and_test.yml +++ b/.github/workflows/CI_build_and_test.yml @@ -358,7 +358,7 @@ jobs: ${VM_PYTHON3_EXECUTABLE} ${CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir "${BUILD_DIR}" --results-dir "${RESULTS_DIR}/unit" -j ${VM_MAX_PARALLEL_TESTS} fi - if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/unit" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then + if [[ ! "$(cd "${{ env.BUILD_DIR }}/tests_results/unit" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then exit 1 fi @@ -384,7 +384,7 @@ jobs: ${VM_PYTHON3_EXECUTABLE} ${CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${SRC_DIR}" --build-dir "${BUILD_DIR}" --results-dir "${RESULTS_DIR}/scene" -j ${VM_MAX_PARALLEL_TESTS} fi - if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/scene" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then + if [[ ! "$(cd "${{ env.BUILD_DIR }}/tests_results/scene" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then exit 1 fi @@ -410,7 +410,7 @@ jobs: ${VM_PYTHON3_EXECUTABLE} ${REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${SRC_DIR}/examples" --input "${SRC_DIR}/applications" --input "${BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" --legacy-regression -j ${VM_MAX_PARALLEL_TESTS} fi - if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/regression" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then + if [[ ! "$(cd "${{ env.BUILD_DIR }}/tests_results/regression" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then exit 1 fi @@ -478,18 +478,18 @@ jobs: echo "#----------------------------------------#" for testType in 'unit' 'scene' 'regression'; do + capitalized="$(echo "${testType:0:1}" | tr '[:lower:]' '[:upper:]')${testType:1}" + echo -e "${bold}${capitalized}:${normal}" for errorType in 'errors' 'crashes' 'failures'; do - if [ -f "${{ env.BUILD_DIR }}/tests_results/${testType}-tests_${errorType}" ]; then - capitalized="$(echo "${testType:0:1}" | tr '[:lower:]' '[:upper:]')${testType:1}" + if [ -f "${{ env.BUILD_DIR }}/tests_results/${testType}/${testType}_${errorType}.txt" ]; then echo "" - echo -e "${bold}${capitalized} ${errorType}:${normal}" + cat "${{ env.BUILD_DIR }}/tests_results/${testType}/${testType}_${errorType}.txt" echo "" - cat "${{ env.BUILD_DIR }}/tests_results/${testType}-tests_${errorType}" - echo "" - echo "#----------------------------------------#" fi done + echo "#----------------------------------------#" + echo "" done echo -e "${bold}You can download all logs here : ${{ steps.publish-tests-logs.outputs.artifact-url }}${normal}" exit 1 From bb1d3891ae7d175595478c0dbb8fcd9cb9b38fdb Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Wed, 23 Sep 2026 18:10:59 +0200 Subject: [PATCH 09/26] Fix python execution --- .github/workflows/CI_build_and_test.yml | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/.github/workflows/CI_build_and_test.yml b/.github/workflows/CI_build_and_test.yml index d13c0fb7697..d9f970a4e70 100644 --- a/.github/workflows/CI_build_and_test.yml +++ b/.github/workflows/CI_build_and_test.yml @@ -349,7 +349,7 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir ${DOCKER_BUILD_DIR} --results-dir \${RESULTS_DIR}/unit -j \${VM_MAX_PARALLEL_TESTS}" + /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env; \${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir ${DOCKER_BUILD_DIR} --results-dir \${RESULTS_DIR}/unit -j \${VM_MAX_PARALLEL_TESTS}" else echo "Launching unit test suite." @@ -375,7 +375,7 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${DOCKER_SRC_DIR}" --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"\${RESULTS_DIR}/scene\" -j \${VM_MAX_PARALLEL_TESTS}" + /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; \${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${DOCKER_SRC_DIR}" --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"\${RESULTS_DIR}/scene\" -j \${VM_MAX_PARALLEL_TESTS}" else echo "Launching scene test suite." @@ -401,7 +401,7 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "export REGRESSION_DIR="$DOCKER_REGRESSION_DIR"; cd /workspace;. ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; ${VM_PYTHON3_EXECUTABLE} ${DOCKER_REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${DOCKER_SRC_DIR}/examples" --input "${DOCKER_SRC_DIR}/applications" --input "${DOCKER_BUILD_DIR}/external_directories/fetched" --output-logs-errors "\${RESULTS_DIR}/regression" --legacy-regression --jobs \${VM_MAX_PARALLEL_TESTS} " + /bin/bash -c "export REGRESSION_DIR="$DOCKER_REGRESSION_DIR"; cd /workspace;. ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; \${VM_PYTHON3_EXECUTABLE} ${DOCKER_REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${DOCKER_SRC_DIR}/examples" --input "${DOCKER_SRC_DIR}/applications" --input "${DOCKER_BUILD_DIR}/external_directories/fetched" --output-logs-errors "\${RESULTS_DIR}/regression" --legacy-regression --jobs \${VM_MAX_PARALLEL_TESTS} " else echo "Launching regression test suite" From 325f84e6e4bfa352a37d4c19d27b06c9e93e02d5 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Thu, 24 Sep 2026 13:57:31 +0200 Subject: [PATCH 10/26] Better dealing with failures --- .github/workflows/CI_build_and_test.yml | 17 +++++++++++++++-- 1 file changed, 15 insertions(+), 2 deletions(-) diff --git a/.github/workflows/CI_build_and_test.yml b/.github/workflows/CI_build_and_test.yml index d9f970a4e70..6f85df8e09a 100644 --- a/.github/workflows/CI_build_and_test.yml +++ b/.github/workflows/CI_build_and_test.yml @@ -360,8 +360,13 @@ jobs: if [[ ! "$(cd "${{ env.BUILD_DIR }}/tests_results/unit" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then exit 1 + else + if [[ "$(awk -F= '$1=="crashes" {print $2}' ${{ env.BUILD_DIR }}/tests_results/unit/summary.txt)" != '0' || "$(awk -F= '$1=="failures" {print $2}' ${{ env.BUILD_DIR }}/tests_results/unit/summary.txt)" != "0" ]]; then + exit 1 + fi fi + - name: Scene tests id: scene-tests-step if: always() && steps.build-step.outcome == 'success' && inputs.generate-binaries == false && inputs.with-all-tests == true @@ -386,6 +391,10 @@ jobs: if [[ ! "$(cd "${{ env.BUILD_DIR }}/tests_results/scene" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then exit 1 + else + if [[ "$(awk -F= '$1=="crashes" {print $2}' ${{ env.BUILD_DIR }}/tests_results/scene/summary.txt)" != '0' || "$(awk -F= '$1=="failures" {print $2}' ${{ env.BUILD_DIR }}/tests_results/scene/summary.txt)" != "0" ]]; then + exit 1 + fi fi - name: Regression tests @@ -411,7 +420,11 @@ jobs: fi if [[ ! "$(cd "${{ env.BUILD_DIR }}/tests_results/regression" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then - exit 1 + exit 1 + else + if [[ "$(awk -F= '$1=="crashes" {print $2}' ${{ env.BUILD_DIR }}/tests_results/regression/summary.txt)" != '0' || "$(awk -F= '$1=="failures" {print $2}' ${{ env.BUILD_DIR }}/tests_results/regression/summary.txt)" != "0" ]]; then + exit 1 + fi fi @@ -468,7 +481,7 @@ jobs: fi if [[ "${{ inputs.generate-binaries }}" == "false" ]]; then - if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -maxdepth 1 -type f)" != "" ]]; then + if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -mindepth 2 -maxdepth 2 -type f -name 'summary.txt')" != "" ]]; then echo "❌ Tests have resulted in : " echo "" python3 ${{ env.CI_DIR }}/scripts/generate-tests-table.py "${{ env.BUILD_DIR }}/tests_results/" From 2ffa0fd2536be901e6811dc0762edcb7d1519ac5 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Thu, 24 Sep 2026 16:29:33 +0200 Subject: [PATCH 11/26] bootstrap pixi ci launch --- .../workflows/CI_trigger_build_and_tests.yml | 64 ++++++++++++++++--- 1 file changed, 54 insertions(+), 10 deletions(-) diff --git a/.github/workflows/CI_trigger_build_and_tests.yml b/.github/workflows/CI_trigger_build_and_tests.yml index 388ac0ad045..7f2cc72b843 100644 --- a/.github/workflows/CI_trigger_build_and_tests.yml +++ b/.github/workflows/CI_trigger_build_and_tests.yml @@ -40,10 +40,14 @@ on: type: choice description: On which OS run the binaries generation options: - - '["sh-ubuntu_gcc_release"]' - - '["sh-macos_clang_release"]' - - '["sh-ubuntu_gcc_release","sh-macos_clang_release"]' - default: '["sh-ubuntu_gcc_release","sh-macos_clang_release"]' + - '["ubuntu"]' + - '["macos"]' + - '["windows"]' + - '["ubuntu","macos"]' + - '["ubuntu","windows"]' + - '["macos","windows"]' + - '["ubuntu","macos","windows"]' + default: '["ubuntu","macos","windows"]' # PR-related build (open, labels, push) pull_request: @@ -78,7 +82,8 @@ jobs: PR_OWNER_URL: ${{ steps.export-vars.outputs.PR_OWNER_URL }} PR_BRANCH_NAME: ${{ steps.export-vars.outputs.PR_BRANCH_NAME }} PR_COMMIT_SHA: ${{ steps.export-vars.outputs.PR_COMMIT_SHA }} - BUILDER_OS: ${{ steps.export-vars.outputs.BUILDER_OS }} + SH_BUILDER_OS: ${{ steps.export-vars.outputs.SH_BUILDER_OS }} + PIXI_BUILDER_OS: ${{ steps.export-vars.outputs.PIXI_BUILDER_OS }} steps: - name: Default values of environment variables @@ -96,7 +101,8 @@ jobs: echo "PR_OWNER_URL=" >> $GITHUB_ENV # PR_OWNER_URL: "" echo "PR_BRANCH_NAME=" >> $GITHUB_ENV # PR_BRANCH_NAME: "" echo "PR_COMMIT_SHA=HEAD" >> $GITHUB_ENV # PR_COMMIT_SHA: "HEAD" - echo 'BUILDER_OS=["sh-ubuntu_gcc_release"]' >> $GITHUB_ENV # BUILDER_OS: ["sh-ubuntu_gcc_release"] + echo 'SH_BUILDER_OS=["sh-ubuntu_gcc_release","sh-macos_clang_release"]' >> $GITHUB_ENV # BUILDER_OS: ubuntu and maco + echo 'PIXI_BUILDER_OS=["windows-latest"]' >> $GITHUB_ENV # BUILDER_OS: windows - name: Run on dispatch if: ${{ github.event_name == 'workflow_dispatch' }} @@ -134,6 +140,21 @@ jobs: echo "EXTERNAL_PLUGINS=${{ inputs.external-plugins }}" >> $GITHUB_ENV echo "ADDITIONNAL_CMAKE_FLAGS=${{ inputs.additionnal-cmake-flags }}" >> $GITHUB_ENV + if [[ "${{ inputs.builder-os}}" == *"windows"* ]]; then + echo 'PIXI_BUILDER_OS=["windows-latest"]' >> $GITHUB_ENV + else + echo 'PIXI_BUILDER_OS=[]' >> $GITHUB_ENV + fi + + if [[ "${{ inputs.builder-os}}" == *"ubuntu"* && "${{ inputs.builder-os}}" == *"macos"*]]; then + echo 'SH_BUILDER_OS=["sh-ubuntu_gcc_release","sh-macos_clang_release"]' >> $GITHUB_ENV + elif [[ "${{ inputs.builder-os}}" == *"ubuntu"* ]]; then + echo 'SH_BUILDER_OS=["sh-ubuntu_gcc_release"]' >> $GITHUB_ENV + elif [[ "${{ inputs.builder-os}}" == *"macos"* ]]; then + echo 'SH_BUILDER_OS=["sh-macos_clang_release"]' >> $GITHUB_ENV + else + echo 'SH_BUILDER_OS=[]' >> $GITHUB_ENV + fi - name: Set up python uses: actions/setup-python@v5 @@ -159,7 +180,8 @@ jobs: echo "SOFA_COMMIT_SHA=${{ github.sha }}">> $GITHUB_ENV echo "WITH_ALL_TESTS=true" >> $GITHUB_ENV echo "FORCE_FULL_BUILD=true" >> $GITHUB_ENV - echo 'BUILDER_OS=["sh-ubuntu_gcc_release","sh-ubuntu_clang_release","sh-ubuntu_clang_debug","sh-fedora_clang_release","sh-macos_clang_release"]' >> $GITHUB_ENV + echo 'SH_BUILDER_OS=["sh-ubuntu_gcc_release","sh-ubuntu_clang_release","sh-ubuntu_clang_debug","sh-fedora_clang_release","sh-macos_clang_release"]' >> $GITHUB_ENV + echo 'PIXI_BUILDER_OS=["ubuntu-latest", "macos-latest", "macos-15-intel", "windows-latest"]' >> $GITHUB_ENV - name: Run when PR is opened or a commit is pushed in a PR if: ${{ github.event_name == 'pull_request' }} @@ -198,7 +220,8 @@ jobs: echo "PR_OWNER_URL=${PR_OWNER_URL}" >> $GITHUB_OUTPUT echo "PR_BRANCH_NAME=${PR_BRANCH_NAME}" >> $GITHUB_OUTPUT echo "PR_COMMIT_SHA=${PR_COMMIT_SHA}" >> $GITHUB_OUTPUT - echo "BUILDER_OS=${BUILDER_OS}" >> $GITHUB_OUTPUT + echo "SH_BUILDER_OS=${SH_BUILDER_OS}" >> $GITHUB_OUTPUT + echo "PIXI_BUILDER_OS=${PIXI_BUILDER_OS}" >> $GITHUB_OUTPUT # =============================================================== @@ -207,7 +230,7 @@ jobs: # Trigger the build and sharing all parameters from filter_build > outputs build-on: needs: filter_build - if: ${{ github.repository_owner == 'sofa-framework' }} + if: ${{ github.repository_owner == 'sofa-framework' && needs.filter_build.outputs.SH_BUILDER_OS != '[]' }} uses: bakpaul/sofa/.github/workflows/CI_build_and_test.yml@26_09_update_ci_with_new_test_scripts_and_pixi_based_ci_for_windows with: sofa-branch-name: ${{ needs.filter_build.outputs.SOFA_BRANCH_NAME }} @@ -223,4 +246,25 @@ jobs: pr-owner-url: ${{ needs.filter_build.outputs.PR_OWNER_URL }} pr-branch-name: ${{ needs.filter_build.outputs.PR_BRANCH_NAME }} pr-commit-sha: ${{ needs.filter_build.outputs.PR_COMMIT_SHA }} - builder-os: ${{ needs.filter_build.outputs.BUILDER_OS }} + builder-os: ${{ needs.filter_build.outputs.SH_BUILDER_OS }} + + # Trigger the build and sharing all parameters from filter_build > outputs + pixi-ci: + needs: filter_build + if: ${{ github.repository_owner == 'sofa-framework' && needs.filter_build.outputs.PIXI_BUILDER_OS != '[]' }} + uses: bakpaul/sofa/.github/workflows/CI_macos_linux_windows_pixi.yml@26_09_update_ci_with_new_test_scripts_and_pixi_based_ci_for_windows + with: + sofa-branch-name: ${{ needs.filter_build.outputs.SOFA_BRANCH_NAME }} + sofa-commit-sha: ${{ needs.filter_build.outputs.SOFA_COMMIT_SHA }} + preset: ${{ needs.filter_build.outputs.PRESET }} + python-version: ${{ needs.filter_build.outputs.PYTHON_VERSION }} + ci-depends-on: ${{ needs.filter_build.outputs.CI_DEPENDS_ON }} + with-all-tests: ${{ needs.filter_build.outputs.WITH_ALL_TESTS == 'true'}} + force-full-build: ${{ needs.filter_build.outputs.FORCE_FULL_BUILD == 'true'}} + external-plugins: ${{ needs.filter_build.outputs.EXTERNAL_PLUGINS }} + additionnal-cmake-flags: ${{ needs.filter_build.outputs.ADDITIONNAL_CMAKE_FLAGS }} + generate-binaries: ${{ needs.filter_build.outputs.GENERATE_BINARIES == 'true'}} + pr-owner-url: ${{ needs.filter_build.outputs.PR_OWNER_URL }} + pr-branch-name: ${{ needs.filter_build.outputs.PR_BRANCH_NAME }} + pr-commit-sha: ${{ needs.filter_build.outputs.PR_COMMIT_SHA }} + builder-os: ${{ needs.filter_build.outputs.PIXI_BUILDER_OS }} From 65df1c234ad26e3647e8f06097e4a69b4a4d2663 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Thu, 24 Sep 2026 16:31:12 +0200 Subject: [PATCH 12/26] TO REVERT, use working ci branch in trigger build and test --- .github/workflows/CI_trigger_build_and_tests.yml | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/.github/workflows/CI_trigger_build_and_tests.yml b/.github/workflows/CI_trigger_build_and_tests.yml index 7f2cc72b843..430873c3f14 100644 --- a/.github/workflows/CI_trigger_build_and_tests.yml +++ b/.github/workflows/CI_trigger_build_and_tests.yml @@ -169,8 +169,8 @@ jobs: - name: Check out code uses: actions/checkout@v5 with: - repository: sofa-framework/ci - ref: master + repository: bakpaul/ci + ref: 26_09_final_jenkins_2_github_migration path: ./ci - name: Check push on master case (e.g. merge) From c314a2e3b5aabd71bedf22ba3a1407ca49b3627d Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Thu, 24 Sep 2026 18:15:13 +0200 Subject: [PATCH 13/26] First try for pixi-based CI --- .../workflows/CI_macos_linux_windows_pixi.yml | 433 +++++++++++++++++- 1 file changed, 409 insertions(+), 24 deletions(-) diff --git a/.github/workflows/CI_macos_linux_windows_pixi.yml b/.github/workflows/CI_macos_linux_windows_pixi.yml index 7016e0ae9d3..05a93851554 100644 --- a/.github/workflows/CI_macos_linux_windows_pixi.yml +++ b/.github/workflows/CI_macos_linux_windows_pixi.yml @@ -1,50 +1,435 @@ name: CI - MacOS/Linux/Windows via Pixi on: - push: - branches: - - master - pull_request: - paths: - - 'pixi*' - workflow_dispatch: + workflow_call: + inputs: + sofa-branch-name: + type: string + required: true + sofa-commit-sha: + type: string + required: true + pr-owner-url: + type: string + required: false + pr-branch-name: + type: string + required: false + pr-commit-sha: + type: string + required: false + preset: + type: string + required: true + python-version: + type: string + required: true + ci-depends-on: + type: string + required: false + with-all-tests: + type: boolean + required: false + default: false + force-full-build: + type: boolean + required: false + default: false + generate-binaries: + type: boolean + required: false + default: false + external-plugins: + type: string + required: false + additionnal-cmake-flags: + type: string + required: false + builder-os: + type: string + required: true + default: '["ubuntu-latest", "macos-latest", "macos-15-intel", "windows-latest"]' + dash-info: + type: string + required: false + default: 'NONE' + description: 'Json scructure with three parameters {"COMMIT_HASH":"fullhsashofthecommit", }' concurrency: group: ${{ github.workflow }}-${{ github.ref }} cancel-in-progress: true jobs: - sofa-pixi: - name: ${{ matrix.os }} - Env ${{ matrix.environment }} ${{ matrix.build_type }} ${{ matrix.compiler }} - runs-on: ${{ matrix.os }} - if: ${{ github.repository_owner == 'sofa-framework' }} + display-inputs: + runs-on: ubuntu-latest + steps: + - name: Display + shell: bash + run: | + echo "Build and test launched with following parameters:" + echo "sofa-branch-name : ${{ inputs.sofa-branch-name }}" + echo "sofa-commit-sha : ${{ inputs.sofa-commit-sha }}" + echo "pr-owner-url : ${{ inputs.pr-owner-url }}" + echo "pr-branch-name : ${{ inputs.pr-branch-name }}" + echo "pr-commit-sha : ${{ inputs.pr-commit-sha }}" + echo "preset : ${{ inputs.preset }}" + echo "ci-depends-on : ${{ inputs.ci-depends-on }}" + echo "with-all-tests : ${{ inputs.with-all-tests }}" + echo "force-full-build : ${{ inputs.force-full-build }}" + echo "generate-binaries : ${{ inputs.generate-binaries }}" + echo "external-plugins : ${{ inputs.external-plugins }}" + echo "additionnal-cmake-flags : ${{ inputs.additionnal-cmake-flags }}" + echo "builder-os : ${{ inputs.builder-os }}" + echo "" + echo "The following python version has been passed : ${{ inputs.python-version }}" + echo "--> only the default python version written in the pixi.toml can be used and will be forced here." + sofa-pixi: strategy: - fail-fast: false - matrix: - os: [ubuntu-latest, macos-latest, macos-15-intel, windows-latest] - environment: [supported-plugins] - build_type: [Release] + fail-fast: false + matrix: + os: ${{ fromJson(inputs.builder-os) }} + build_type: [Release] + runs-on: ${{ matrix.os }} + name: ${{ matrix.os }} - Env ${{ inputs.preset }} ${{ matrix.build_type }} ${{ matrix.compiler }} steps: - uses: actions/checkout@v4 + with: + ref: ${{ inputs.sofa-branch-name }} + path: sofa + + - run: git config --global user.email "<>" + - run: git config --global user.name "SOFA Bot" + + - name: Setup SOFA and clone CI + shell: bash -el {0} + run: | + export WORKSPACE=$GITHUB_WORKSPACE + echo "WORKSPACE=$WORKSPACE" >> $GITHUB_ENV + + export SRC_DIR=$GITHUB_WORKSPACE/sofa + echo "SRC_DIR=$SRC_DIR" >> $GITHUB_ENV + + cd $SRC_DIR + if [ ! -z "${{ inputs.pr-owner-url }}" ]; then + echo "This is a PR, merging branch ${{ inputs.pr-branch-name }} from remote ${{ inputs.pr-owner-url }} into origin branch ${{ inputs.sofa-branch-name }}" + git remote add pr ${{ inputs.pr-owner-url }} + git fetch pr + + if [ "${{ inputs.pr-commit-sha }}" == "HEAD" ]; then + git merge ${{ inputs.pr-branch-name }} + else + git merge ${{ inputs.pr-commit-sha }} + fi + else + echo "This is not a PR: checking out sha ${{ inputs.sofa-commit-sha }} from branch ${{ inputs.sofa-branch-name }}" + git checkout ${{ inputs.sofa-commit-sha }} + fi + + cd $WORKSPACE + + ## Clone CI and use ci-depends-on structure + ci_branch=${{ inputs.sofa-branch-name }} + ci_repo_url="https://www.github.com/sofa-framework/ci" + + + # check if ci has a ci-depends-on + ci_ci_depends_on=$(echo "${{ inputs.ci-depends-on }}" | jq .ci) + if [ -n "${{ inputs.ci-depends-on }}" ] && [ "$ci_ci_depends_on" != "null" ]; then + echo "ci-depends-on for ci repository detected." + ci_repo_url=$(echo "${{ inputs.ci-depends-on }}" | jq .ci.repo_url) + ci_branch=$(echo "${{ inputs.ci-depends-on }}" | jq .ci.branch_name) + fi + echo "CI_BRANCH=$ci_branch" >> $GITHUB_ENV + + + echo "Cloning CI from remote ${ci_repo_url}, selecting branch ${ci_branch}" + + CI_DIR=$WORKSPACE/ci + echo "CI_DIR=$CI_DIR" >> $GITHUB_ENV + + git clone -b ${ci_branch//\"} --single-branch ${ci_repo_url//\"} + + + + ## Clone Regression and use ci-depends-on structure + regression_branch=${{ inputs.sofa-branch-name }} + regression_repo_url="https://www.github.com/sofa-framework/Regression" + + + # check if ci has a ci-depends-on + regression_ci_depends_on=$(echo "${{ inputs.ci-depends-on }}" | jq .Regression) + if [ -n "${{ inputs.ci-depends-on }}" ] && [ "$regression_ci_depends_on" != "null" ]; then + echo "ci-depends-on for Regression repository detected." + regression_repo_url=$(echo "${{ inputs.ci-depends-on }}" | jq .Regression.repo_url) + regression_branch=$(echo "${{ inputs.ci-depends-on }}" | jq .Regression.branch_name) + fi + echo "REGRESSION_BRANCH=$regression_branch" >> $GITHUB_ENV + + + echo "Cloning Regression from remote ${regression_repo_url}, selecting branch ${regression_branch}" + + REGRESSION_DIR=$WORKSPACE/Regression + echo "REGRESSION_DIR=$REGRESSION_DIR" >> $GITHUB_ENV + + git clone -b ${regression_branch//\"} --single-branch ${regression_repo_url//\"} + + + cd $WORKSPACE + + ## Setup build folder + mkdir $WORKSPACE/build + + SOFA_BUILD_DIR=$WORKSPACE/build + echo "SOFA_BUILD_DIR=$SOFA_BUILD_DIR" >> $GITHUB_ENV + SOFA_INSTALL_PREFIX=$WORKSPACE/install + echo "SOFA_INSTALL_PREFIX=$SOFA_INSTALL_PREFIX" >> $GITHUB_ENV + + if [ -n "${{ inputs.external-plugins }}" ]; then + echo "Setting up external plugins." + for plugin in ${{ inputs.external-plugins }}; do + plugin_base=${plugin%@*} + plugin_branch=${plugin##*@} + plugin_repo=$(basename "$plugin_base") + + echo "Adding line 'sofa_add_external(plugin $plugin_repo GIT_REF $plugin_branch GIT_REPOSITORY $plugin_base ON)' to file ${SRC_DIR}/applications/CMakeLists.txt" + echo "sofa_add_external(plugin $plugin_repo GIT_REF $plugin_branch GIT_REPOSITORY $plugin_base ON)" >> "${SRC_DIR}/applications/CMakeLists.txt" + done + fi + - uses: prefix-dev/setup-pixi@v0.8.10 with: cache: false - environments: ${{ matrix.environment }} + manifest-path: sofa/pixi.toml + environments: ${{ inputs.preset }} - name: Build SOFA [MacOS/Linux/Windows] + id: build-step shell: bash -el {0} env: SOFA_BUILD_TYPE: ${{ matrix.build_type }} run: | - pixi run -e ${{ matrix.environment }} configure -DCMAKE_CUDA_ARCHITECTURES="75;89;120" - pixi run -e ${{ matrix.environment }} build + cd ${SRC_DIR} - - name: Testing - Run SOFA in batch mode [MacOS/Linux/Windows] - shell: bash -el {0} - env: - SOFA_BUILD_TYPE: ${{ matrix.build_type }} + + ## Deal with ci-depends-on + # Loop over each key-value pair in the JSON avoiding ci repository if inside + CMAKE_OPTIONS="${{inputs.additionnal-cmake-flags}}" + for key in $(echo "${{ inputs.ci-depends-on }}" | jq -r 'keys[]' | grep -v '^ci$'); do + + repo_url=$(echo "${{ inputs.ci-depends-on }}" | jq -r ".\"$key\".repo_url") + branch_name=$(echo "${{ inputs.ci-depends-on }}" | jq -r ".\"$key\".branch_name") + + # Format the CMake flags for this key and append to the result + fixed_name=$(echo "$key" | awk '{gsub(/\./, "_"); print toupper($0)}') + flag_repository="-D${fixed_name}_GIT_REPOSITORY=\"$repo_url\"" + flag_tag="-D${fixed_name}_GIT_TAG=\"$branch_name\"" + + # Append both flags to the result string with a space + CMAKE_OPTIONS="$CMAKE_OPTIONS $flag_repository $flag_tag " + done + + if [[ ! -n "$CMAKE_OPTIONS" ]]; then + echo "No ci-depends-on detected." + else + echo "Adding the following cmake variable : $CMAKE_OPTIONS" + fi + + ## Run build step + pixi run -e ${{ inputs.preset }} configure $CMAKE_OPTIONS + pixi run -e ${{ inputs.preset }} build + + - name: Setup env for tests + shell: bash + if: always() && ${{ runner.os == 'Windows' }} run: | - pixi run -e ${{ matrix.environment }} runSofa -g batch + cd ${SRC_DIR} + PIXI_PREFIX="$(pwd -W)/.pixi/envs/${{ inputs.preset }}/" + echo "VM_PYTHON3_EXECUTABLE=$PIXI_PREFIX/python.exe" >> $GITHUB_ENV + echo "PIXI_PREFIX=$PIXI_PREFIX" >> $GITHUB_ENV + + . ${CI_DIR}/scripts/setup-test-env.sh ${SOFA_BUILD_DIR} ${SRC_DIR}/scripts default none + + + echo "BUILD_DIR=$(cd "$SOFA_BUILD_DIR" && pwd -W)" >> $GITHUB_ENV + echo "SRC_DIR=$(cd "$SRC_DIR" && pwd -W)" >> $GITHUB_ENV + echo "CI_DIR=$(cd "$CI_DIR" && pwd -W)" >> $GITHUB_ENV + echo "REGRESSION_DIR=$(cd "$REGRESSION_DIR" && pwd -W)" >> $GITHUB_ENV + echo "PYTHONPATH=$PYTHONPATH" >> $GITHUB_ENV + echo "SOFA_ROOT=$SOFA_ROOT" >> $GITHUB_ENV + echo "RESULTS_DIR=$RESULTS_DIR" >> $GITHUB_ENV + echo "VM_MAX_PARALLEL_TESTS=$VM_MAX_PARALLEL_TESTS" >> $GITHUB_ENV + + + if [[ "$RUNNER_OS" == "Windows" ]]; then + #Activating pixi env in a git-bash terminal is broken, here we just want to consume it. + + echo "PIXI_PREFIX=$PIXI_PREFIX" >> $GITHUB_ENV + + echo "$PIXI_PREFIX" >> $GITHUB_PATH + echo "$PIXI_PREFIX/bin" >> $GITHUB_PATH + echo "$PIXI_PREFIX/Library/bin" >> $GITHUB_PATH + echo "$PIXI_PREFIX/Scripts" >> $GITHUB_PATH + echo "$PIXI_PREFIX/Library/mingw-w64/bin" >> $GITHUB_PATH + echo "$PIXI_PREFIX/Library/usr/bin" >> $GITHUB_PATH + echo "$PIXI_PREFIX/sofa-build/bin/" >> $GITHUB_PATH + fi + + exit 0 + + - name: Unit tests + id: unit-tests-step + if: always() && ${{ runner.os == 'Windows' }} && steps.build-step.outcome == 'success' && inputs.generate-binaries == false + shell: cmd + run: | + cd /d "%SRC_DIR%" + + set "UNIT_RESULTS_DIR=%BUILD_DIR%\tests_results\unit" + + pixi run -e ${{ inputs.preset }} python %CI_DIR%\scripts\tests\sofa_unit_tests.py --build-dir "%BUILD_DIR%" --results-dir "%UNIT_RESULTS_DIR%" -j %VM_MAX_PARALLEL_TESTS% + + if not exist "%UNIT_RESULTS_DIR%\*summary*" exit /b 1 + + set "CRASHES=" + set "FAILURES=" + for /f "usebackq tokens=1,2 delims==" %%a in ("%UNIT_RESULTS_DIR%\summary.txt") do ( + if "%%a"=="crashes" set "CRASHES=%%b" + if "%%a"=="failures" set "FAILURES=%%b" + ) + + if not "%CRASHES%"=="0" exit /b 1 + if not "%FAILURES%"=="0" exit /b 1 + + - name: Scene tests + id: scene-tests-step + if: always() && ${{ runner.os == 'Windows' }} && steps.build-step.outcome == 'success' && inputs.generate-binaries == false && inputs.with-all-tests == true + shell: cmd + run: | + cd /d "%SRC_DIR%" + + set "SCENE_RESULTS_DIR=%BUILD_DIR%\tests_results\scene" + + pixi run -e ${{ inputs.preset }} python %CI_DIR%\scripts\tests\sofa_scene_tests.py --src-dir "%SRC_DIR%" --build-dir "%BUILD_DIR%" --results-dir "%SCENE_RESULTS_DIR%" -j %VM_MAX_PARALLEL_TESTS% + + if not exist "%SCENE_RESULTS_DIR%\*summary*" exit /b 1 + + set "CRASHES=" + set "FAILURES=" + for /f "usebackq tokens=1,2 delims==" %%a in ("%SCENE_RESULTS_DIR%\summary.txt") do ( + if "%%a"=="crashes" set "CRASHES=%%b" + if "%%a"=="failures" set "FAILURES=%%b" + ) + + if not "%CRASHES%"=="0" exit /b 1 + if not "%FAILURES%"=="0" exit /b 1 + + - name: Regression tests + id: regression-tests-step + if: always() && ${{ runner.os == 'Windows' }} && steps.build-step.outcome == 'success' && inputs.generate-binaries == false && inputs.with-all-tests == true + shell: cmd + run: | + cd /d "%SRC_DIR%" + + set "REG_RESULTS_DIR=%BUILD_DIR%\tests_results\regression" + + pixi run -e ${{ inputs.preset }} python %REGRESSION_DIR%\SofaRegressionProgram\SofaRegressionProgram.py --input "%SRC_DIR%/examples" --input "%SRC_DIR%\applications" --input "%BUILD_DIR%\external_directories\fetched" --output-logs-errors "%REG_RESULTS_DIR%" --legacy-regression -j %VM_MAX_PARALLEL_TESTS% + if not exist "%REG_RESULTS_DIR%\*summary*" exit /b 1 + + set "CRASHES=" + set "FAILURES=" + for /f "usebackq tokens=1,2 delims==" %%a in ("%REG_RESULTS_DIR%\summary.txt") do ( + if "%%a"=="crashes" set "CRASHES=%%b" + if "%%a"=="failures" set "FAILURES=%%b" + ) + + if not "%CRASHES%"=="0" exit /b 1 + if not "%FAILURES%"=="0" exit /b 1 + + + - name: Publish artifacts + if: steps.build-step.outcome == 'success' && inputs.generate-binaries == true + uses: actions/upload-artifact@v4 + with: + name: binaries_${{ matrix.os }} + path: | + ${{ env.SOFA_BUILD_DIR }}/SOFA_v* + + + - name: Publish tests logs + id: publish-tests-logs + if: always() && ${{ runner.os == 'Windows' }} + uses: actions/upload-artifact@v4 + with: + name: tests-logs_${{ matrix.os }} + path: | + ${{ env.SOFA_BUILD_DIR }}/tests_results/ + + + - name: Configure python for display + if: always() && ${{ runner.os == 'Windows' }} + shell: bash + run: | + python3 -m pip install prettytable + + - name: Summarize results + if: always() && ${{ runner.os == 'Windows' }} + shell: bash + run: | + + bold="\033[1m" + normal="\033[0m" + if [[ "${{ steps.configure.outcome }}" == "failure" || "${{ steps.clone.outcome }}" == "failure" ]]; then + echo "❌ Something whent wrong during the configure or clone steps..." + echo -e "${bold}Please check those actions logs${normal}" + exit 1 + else + echo "✅ Setup OK." + fi + + if [[ "${{ steps.build-step.outcome }}" == "failure" ]]; then + echo "❌ Build step failed" + echo -e "${bold}You can download all logs here : ${{ steps.publish-build-logs.outputs.artifact-url }}${normal}" + exit 1 + else + echo "✅ Build OK." + fi + + if [[ "${{ inputs.generate-binaries }}" == "false" ]]; then + if [[ "$(cd "${{ env.SOFA_BUILD_DIR }}/tests_results/" && find . -maxdepth 1 -type f)" != "" ]]; then + echo "❌ Tests have resulted in : " + echo "" + python3 ${{ env.CI_DIR }}/scripts/generate-tests-table.py "${{ env.SOFA_BUILD_DIR }}/tests_results/" + echo "" + echo "#----------------------------------------#" + echo "#---------------Quick Logs---------------#" + echo "#----------------------------------------#" + for testType in 'unit' 'scene' 'regression'; + do + for errorType in 'errors' 'crashes' 'failures'; + do + if [ -f "${{ env.SOFA_BUILD_DIR }}/tests_results/${testType}-tests_${errorType}" ]; then + capitalized="$(echo "${testType:0:1}" | tr '[:lower:]' '[:upper:]')${testType:1}" + echo "" + echo -e "${bold}${capitalized} ${errorType}:${normal}" + echo "" + cat "${{ env.SOFA_BUILD_DIR }}/tests_results/${testType}-tests_${errorType}" + echo "" + echo "#----------------------------------------#" + fi + done + done + echo -e "${bold}You can download all logs here : ${{ steps.publish-tests-logs.outputs.artifact-url }}${normal}" + exit 1 + elif [[ "${{ steps.unit-tests-step.outcome }}" == "failure" || "${{ steps.scene-tests-step.outcome }}" == "failure" || "${{ steps.regression-tests-step.outcome }}" == "failure" ]]; then + echo "❌ Something whent wrong during one of the tests steps" + echo -e "${bold}Please check this action logs, and download tests logs here: ${{ steps.publish-tests-logs.outputs.artifact-url }}${normal}" + exit 1 + else + echo "✅ Tests where successful : " + echo "" + python3 ${{ env.CI_DIR }}/scripts/generate-tests-table.py "${{ env.SOFA_BUILD_DIR }}/tests_results/" + echo "" + fi + fi From f42d516a2813bb63a3a7dfcf5e83064c13988368 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Thu, 24 Sep 2026 18:19:35 +0200 Subject: [PATCH 14/26] Fix merge for pixi --- .github/workflows/CI_macos_linux_windows_pixi.yml | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/.github/workflows/CI_macos_linux_windows_pixi.yml b/.github/workflows/CI_macos_linux_windows_pixi.yml index 05a93851554..7d3a2fdf3d3 100644 --- a/.github/workflows/CI_macos_linux_windows_pixi.yml +++ b/.github/workflows/CI_macos_linux_windows_pixi.yml @@ -111,9 +111,10 @@ jobs: export SRC_DIR=$GITHUB_WORKSPACE/sofa echo "SRC_DIR=$SRC_DIR" >> $GITHUB_ENV - cd $SRC_DIR if [ ! -z "${{ inputs.pr-owner-url }}" ]; then echo "This is a PR, merging branch ${{ inputs.pr-branch-name }} from remote ${{ inputs.pr-owner-url }} into origin branch ${{ inputs.sofa-branch-name }}" + git clone -b ${{ inputs.sofa-branch-name }} --single-branch https://www.github.com/sofa-framework/sofa + cd sofa git remote add pr ${{ inputs.pr-owner-url }} git fetch pr @@ -124,6 +125,8 @@ jobs: fi else echo "This is not a PR: checking out sha ${{ inputs.sofa-commit-sha }} from branch ${{ inputs.sofa-branch-name }}" + git clone -b ${{ inputs.sofa-branch-name }} --single-branch https://www.github.com/sofa-framework/sofa + cd sofa git checkout ${{ inputs.sofa-commit-sha }} fi From 81db71513a52b3c2a04ba07f40c8aeadaa786a72 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Thu, 24 Sep 2026 18:23:41 +0200 Subject: [PATCH 15/26] Check if directory exists --- .github/workflows/CI_macos_linux_windows_pixi.yml | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/.github/workflows/CI_macos_linux_windows_pixi.yml b/.github/workflows/CI_macos_linux_windows_pixi.yml index 7d3a2fdf3d3..ed586d8e4ba 100644 --- a/.github/workflows/CI_macos_linux_windows_pixi.yml +++ b/.github/workflows/CI_macos_linux_windows_pixi.yml @@ -111,6 +111,10 @@ jobs: export SRC_DIR=$GITHUB_WORKSPACE/sofa echo "SRC_DIR=$SRC_DIR" >> $GITHUB_ENV + if [ -d "$SRC_DIR" ]; then + rm -rf "$SRC_DIR" + fi + if [ ! -z "${{ inputs.pr-owner-url }}" ]; then echo "This is a PR, merging branch ${{ inputs.pr-branch-name }} from remote ${{ inputs.pr-owner-url }} into origin branch ${{ inputs.sofa-branch-name }}" git clone -b ${{ inputs.sofa-branch-name }} --single-branch https://www.github.com/sofa-framework/sofa From 43c3007fb146018f24245e0bf218aea7e942ae58 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Fri, 25 Sep 2026 09:43:55 +0200 Subject: [PATCH 16/26] Fix input for setup test script --- .github/workflows/CI_macos_linux_windows_pixi.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/CI_macos_linux_windows_pixi.yml b/.github/workflows/CI_macos_linux_windows_pixi.yml index ed586d8e4ba..e4fa3f468e8 100644 --- a/.github/workflows/CI_macos_linux_windows_pixi.yml +++ b/.github/workflows/CI_macos_linux_windows_pixi.yml @@ -257,7 +257,7 @@ jobs: echo "VM_PYTHON3_EXECUTABLE=$PIXI_PREFIX/python.exe" >> $GITHUB_ENV echo "PIXI_PREFIX=$PIXI_PREFIX" >> $GITHUB_ENV - . ${CI_DIR}/scripts/setup-test-env.sh ${SOFA_BUILD_DIR} ${SRC_DIR}/scripts default none + . ${CI_DIR}/scripts/setup-test-env.sh ${SOFA_BUILD_DIR} ${CI_DIR}/scripts default none echo "BUILD_DIR=$(cd "$SOFA_BUILD_DIR" && pwd -W)" >> $GITHUB_ENV From 9444a9af017d9a9822392b61e3364480b709574f Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Fri, 25 Sep 2026 14:52:00 +0200 Subject: [PATCH 17/26] fix build dir --- development/scripts/pixi/activation.bat | 2 +- development/scripts/pixi/activation.sh | 8 +++++++- 2 files changed, 8 insertions(+), 2 deletions(-) diff --git a/development/scripts/pixi/activation.bat b/development/scripts/pixi/activation.bat index 581e19f9dbb..1b0c3ae7748 100644 --- a/development/scripts/pixi/activation.bat +++ b/development/scripts/pixi/activation.bat @@ -7,7 +7,7 @@ set CMAKE_EXPORT_COMPILE_COMMANDS=1 set CMAKE_COLOR_DIAGNOSTICS=1 :: Each environment have its dedicated build dir -set SOFA_BUILD_DIR=%CONDA_PREFIX%\sofa-build +if not defined SOFA_BUILD_DIR (set SOFA_BUILD_DIR=%CONDA_PREFIX%\sofa-build) :: Set default build value only if not previously set if not defined SOFA_CMAKE_PREFIX_PATH (set SOFA_CMAKE_PREFIX_PATH=%CONDA_PREFIX%) diff --git a/development/scripts/pixi/activation.sh b/development/scripts/pixi/activation.sh index 7006e4ea364..059d3b3580e 100644 --- a/development/scripts/pixi/activation.sh +++ b/development/scripts/pixi/activation.sh @@ -10,7 +10,13 @@ export CMAKE_COLOR_DIAGNOSTICS=1 # Set default build value only if not previously set export CMAKE_PREFIX_PATH=$CONDA_PREFIX # Each environment have its dedicated build dir -export SOFA_BUILD_DIR=$CONDA_PREFIX/sofa-build +if [[ -z "$SOFA_BUILD_DIR" ]]; then + export SOFA_BUILD_DIR=$CONDA_PREFIX/sofa-build +fi +if [[ -z "$SOFA_INSTALL_PREFIX" ]]; then + export SOFA_INSTALL_PREFIX=$CONDA_PREFIX/ +fi + export SOFA_BUILD_TYPE=${SOFA_BUILD_TYPE:=Release} export SOFA_PYTHON_EXECUTABLE=${SOFA_PYTHON_EXECUTABLE:=$CONDA_PREFIX/bin/python} export SOFA_BUILD_RELEASE_PACKAGE_WITH_PIXI=0 From 9efe3081792f797c60bb7daf62e685ca104ab0f5 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Fri, 25 Sep 2026 17:26:06 +0200 Subject: [PATCH 18/26] Fix ci script + filter scenes for cuda --- .../workflows/CI_macos_linux_windows_pixi.yml | 25 +++++++--------- .../plugins/SofaCUDA/examples/.scene-tests | 30 +++++++++---------- 2 files changed, 26 insertions(+), 29 deletions(-) diff --git a/.github/workflows/CI_macos_linux_windows_pixi.yml b/.github/workflows/CI_macos_linux_windows_pixi.yml index e4fa3f468e8..fbdc7a377eb 100644 --- a/.github/workflows/CI_macos_linux_windows_pixi.yml +++ b/.github/workflows/CI_macos_linux_windows_pixi.yml @@ -55,10 +55,6 @@ on: default: 'NONE' description: 'Json scructure with three parameters {"COMMIT_HASH":"fullhsashofthecommit", }' -concurrency: - group: ${{ github.workflow }}-${{ github.ref }} - cancel-in-progress: true - jobs: display-inputs: runs-on: ubuntu-latest @@ -103,6 +99,7 @@ jobs: - run: git config --global user.name "SOFA Bot" - name: Setup SOFA and clone CI + id: clone shell: bash -el {0} run: | export WORKSPACE=$GITHUB_WORKSPACE @@ -288,7 +285,7 @@ jobs: - name: Unit tests id: unit-tests-step - if: always() && ${{ runner.os == 'Windows' }} && steps.build-step.outcome == 'success' && inputs.generate-binaries == false + if: always() && runner.os == 'Windows' && steps.build-step.outcome == 'success' && inputs.generate-binaries == false shell: cmd run: | cd /d "%SRC_DIR%" @@ -311,7 +308,7 @@ jobs: - name: Scene tests id: scene-tests-step - if: always() && ${{ runner.os == 'Windows' }} && steps.build-step.outcome == 'success' && inputs.generate-binaries == false && inputs.with-all-tests == true + if: always() && runner.os == 'Windows' && steps.build-step.outcome == 'success' && inputs.generate-binaries == false && inputs.with-all-tests == true shell: cmd run: | cd /d "%SRC_DIR%" @@ -334,7 +331,7 @@ jobs: - name: Regression tests id: regression-tests-step - if: always() && ${{ runner.os == 'Windows' }} && steps.build-step.outcome == 'success' && inputs.generate-binaries == false && inputs.with-all-tests == true + if: always() && runner.os == 'Windows' && steps.build-step.outcome == 'success' && inputs.generate-binaries == false && inputs.with-all-tests == true shell: cmd run: | cd /d "%SRC_DIR%" @@ -356,7 +353,7 @@ jobs: - name: Publish artifacts - if: steps.build-step.outcome == 'success' && inputs.generate-binaries == true + if: always() && steps.build-step.outcome == 'success' && inputs.generate-binaries == true uses: actions/upload-artifact@v4 with: name: binaries_${{ matrix.os }} @@ -366,7 +363,7 @@ jobs: - name: Publish tests logs id: publish-tests-logs - if: always() && ${{ runner.os == 'Windows' }} + if: always() && runner.os == 'Windows' uses: actions/upload-artifact@v4 with: name: tests-logs_${{ matrix.os }} @@ -375,20 +372,20 @@ jobs: - name: Configure python for display - if: always() && ${{ runner.os == 'Windows' }} + if: always() && runner.os == 'Windows' shell: bash run: | python3 -m pip install prettytable - name: Summarize results - if: always() && ${{ runner.os == 'Windows' }} + if: always() && runner.os == 'Windows' shell: bash run: | bold="\033[1m" normal="\033[0m" - if [[ "${{ steps.configure.outcome }}" == "failure" || "${{ steps.clone.outcome }}" == "failure" ]]; then - echo "❌ Something whent wrong during the configure or clone steps..." + if [[ "${{ steps.clone.outcome }}" == "failure" ]]; then + echo "❌ Something whent wrong during the clone steps..." echo -e "${bold}Please check those actions logs${normal}" exit 1 else @@ -397,7 +394,7 @@ jobs: if [[ "${{ steps.build-step.outcome }}" == "failure" ]]; then echo "❌ Build step failed" - echo -e "${bold}You can download all logs here : ${{ steps.publish-build-logs.outputs.artifact-url }}${normal}" + echo -e "${bold}Please check those actions logs${normal}" exit 1 else echo "✅ Build OK." diff --git a/applications/plugins/SofaCUDA/examples/.scene-tests b/applications/plugins/SofaCUDA/examples/.scene-tests index f40de927183..b2dde060046 100644 --- a/applications/plugins/SofaCUDA/examples/.scene-tests +++ b/applications/plugins/SofaCUDA/examples/.scene-tests @@ -35,18 +35,18 @@ ignore "TetrahedronFEM_with_SpringForceField.scn" ignore "CudaCorotationalFEMForceField.scn" ignore "CudaLinearSmallStrainFEMForceField.scn" -ignore "CudaCorotationalFEMForceField_hexa.scn" -ignore "CudaCorotationalFEMForceField_quad.scn" -ignore "CudaCorotationalFEMForceField_tetra.scn" -ignore "CudaCorotationalFEMForceField_triangle.scn" -ignore "CudaCorotationalFEMForceField_prism.scn" -ignore "CudaCorotationalFEMForceField_pyramid.scn" -ignore "CudaLinearSmallStrainFEMForceField_hexa.scn" -ignore "CudaLinearSmallStrainFEMForceField_quad.scn" -ignore "CudaLinearSmallStrainFEMForceField_tetra.scn" -ignore "CudaLinearSmallStrainFEMForceField_triangle.scn" -ignore "CudaLinearSmallStrainFEMForceField_prism.scn" -ignore "CudaLinearSmallStrainFEMForceField_pyramid.scn" -ignore "CorotationalFEMForceField_tetra_cpu_gpu.scn" -ignore "Tetrahedron_corotational.py" -ignore "Hexahedron_corotational.py" +ignore "ElementFEMForcefield/CudaCorotationalFEMForceField_hexa.scn" +ignore "ElementFEMForcefield/CudaCorotationalFEMForceField_quad.scn" +ignore "ElementFEMForcefield/CudaCorotationalFEMForceField_tetra.scn" +ignore "ElementFEMForcefield/CudaCorotationalFEMForceField_triangle.scn" +ignore "ElementFEMForcefield/CudaCorotationalFEMForceField_prism.scn" +ignore "ElementFEMForcefield/CudaCorotationalFEMForceField_pyramid.scn" +ignore "ElementFEMForcefield/CudaLinearSmallStrainFEMForceField_hexa.scn" +ignore "ElementFEMForcefield/CudaLinearSmallStrainFEMForceField_quad.scn" +ignore "ElementFEMForcefield/CudaLinearSmallStrainFEMForceField_tetra.scn" +ignore "ElementFEMForcefield/CudaLinearSmallStrainFEMForceField_triangle.scn" +ignore "ElementFEMForcefield/CudaLinearSmallStrainFEMForceField_prism.scn" +ignore "ElementFEMForcefield/CudaLinearSmallStrainFEMForceField_pyramid.scn" +ignore "cpu-gpu_validation/CorotationalFEMForceField_tetra_cpu_gpu.scn" +ignore "benchmarks/Tetrahedron_corotational.py" +ignore "benchmarks/Hexahedron_corotational.py" From f1a60d73364f05a37f2897ab8186059c3039a80c Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Mon, 28 Sep 2026 08:56:00 +0200 Subject: [PATCH 19/26] Try to launch out of the pixi shell --- .../workflows/CI_macos_linux_windows_pixi.yml | 22 ++++++++++++++++--- 1 file changed, 19 insertions(+), 3 deletions(-) diff --git a/.github/workflows/CI_macos_linux_windows_pixi.yml b/.github/workflows/CI_macos_linux_windows_pixi.yml index fbdc7a377eb..ce9ae585970 100644 --- a/.github/workflows/CI_macos_linux_windows_pixi.yml +++ b/.github/workflows/CI_macos_linux_windows_pixi.yml @@ -292,7 +292,12 @@ jobs: set "UNIT_RESULTS_DIR=%BUILD_DIR%\tests_results\unit" - pixi run -e ${{ inputs.preset }} python %CI_DIR%\scripts\tests\sofa_unit_tests.py --build-dir "%BUILD_DIR%" --results-dir "%UNIT_RESULTS_DIR%" -j %VM_MAX_PARALLEL_TESTS% + REM Activate the environment in the terminal + pixi shell-hook --shell cmd -e ${{ inputs.preset }} > "%TEMP%\pixi_hook.bat" + call "%TEMP%\pixi_hook.bat" + del "%TEMP%\pixi_hook.bat" + + python %CI_DIR%\scripts\tests\sofa_unit_tests.py --build-dir "%BUILD_DIR%" --results-dir "%UNIT_RESULTS_DIR%" -j %VM_MAX_PARALLEL_TESTS% if not exist "%UNIT_RESULTS_DIR%\*summary*" exit /b 1 @@ -315,7 +320,12 @@ jobs: set "SCENE_RESULTS_DIR=%BUILD_DIR%\tests_results\scene" - pixi run -e ${{ inputs.preset }} python %CI_DIR%\scripts\tests\sofa_scene_tests.py --src-dir "%SRC_DIR%" --build-dir "%BUILD_DIR%" --results-dir "%SCENE_RESULTS_DIR%" -j %VM_MAX_PARALLEL_TESTS% + REM Activate the environment in the terminal + pixi shell-hook --shell cmd -e ${{ inputs.preset }} > "%TEMP%\pixi_hook.bat" + call "%TEMP%\pixi_hook.bat" + del "%TEMP%\pixi_hook.bat" + + python %CI_DIR%\scripts\tests\sofa_scene_tests.py --src-dir "%SRC_DIR%" --build-dir "%BUILD_DIR%" --results-dir "%SCENE_RESULTS_DIR%" -j %VM_MAX_PARALLEL_TESTS% if not exist "%SCENE_RESULTS_DIR%\*summary*" exit /b 1 @@ -338,7 +348,13 @@ jobs: set "REG_RESULTS_DIR=%BUILD_DIR%\tests_results\regression" - pixi run -e ${{ inputs.preset }} python %REGRESSION_DIR%\SofaRegressionProgram\SofaRegressionProgram.py --input "%SRC_DIR%/examples" --input "%SRC_DIR%\applications" --input "%BUILD_DIR%\external_directories\fetched" --output-logs-errors "%REG_RESULTS_DIR%" --legacy-regression -j %VM_MAX_PARALLEL_TESTS% + REM Activate the environment in the terminal + pixi shell-hook --shell cmd -e ${{ inputs.preset }} > "%TEMP%\pixi_hook.bat" + call "%TEMP%\pixi_hook.bat" + del "%TEMP%\pixi_hook.bat" + + + python %REGRESSION_DIR%\SofaRegressionProgram\SofaRegressionProgram.py --input "%SRC_DIR%/examples" --input "%SRC_DIR%\applications" --input "%BUILD_DIR%\external_directories\fetched" --output-logs-errors "%REG_RESULTS_DIR%" --legacy-regression -j %VM_MAX_PARALLEL_TESTS% if not exist "%REG_RESULTS_DIR%\*summary*" exit /b 1 set "CRASHES=" From e5b7caa035afd31ceaf1aa0d3aac23ddc6af9ea0 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Mon, 28 Sep 2026 10:07:19 +0200 Subject: [PATCH 20/26] Revert changes on UNIX CI as #6325 supersed it --- .github/workflows/CI_build_and_test.yml | 84 ++++--------------- .../workflows/CI_trigger_build_and_tests.yml | 2 +- 2 files changed, 19 insertions(+), 67 deletions(-) diff --git a/.github/workflows/CI_build_and_test.yml b/.github/workflows/CI_build_and_test.yml index 6f85df8e09a..6bdef27983d 100644 --- a/.github/workflows/CI_build_and_test.yml +++ b/.github/workflows/CI_build_and_test.yml @@ -103,7 +103,7 @@ jobs: echo "Workspace folder for this build will be $WORKSPACE" - - name: Clone SOFA, CI and Regression + - name: Clone SOFA and CI id: clone shell: bash run: | @@ -170,33 +170,6 @@ jobs: cd $WORKSPACE - ## Clone Regression and use ci-depends-on structure - regression_branch=${{ inputs.sofa-branch-name }} - regression_repo_url="https://www.github.com/sofa-framework/Regression" - - - # check if ci has a ci-depends-on - regression_ci_depends_on=$(echo "${{ inputs.ci-depends-on }}" | jq .Regression) - if [ -n "${{ inputs.ci-depends-on }}" ] && [ "$regression_ci_depends_on" != "null" ]; then - echo "ci-depends-on for Regression repository detected." - regression_repo_url=$(echo "${{ inputs.ci-depends-on }}" | jq .Regression.repo_url) - regression_branch=$(echo "${{ inputs.ci-depends-on }}" | jq .Regression.branch_name) - fi - echo "REGRESSION_BRANCH=$regression_branch" >> $GITHUB_ENV - - - echo "Cloning Regression from remote ${regression_repo_url}, selecting branch ${regression_branch}" - - if [ -d $WORKSPACE/Regression ]; then - rm -rf $WORKSPACE/Regression - fi - REGRESSION_DIR=$WORKSPACE/Regression - echo "REGRESSION_DIR=$REGRESSION_DIR" >> $GITHUB_ENV - - git clone -b ${regression_branch//\"} --single-branch ${regression_repo_url//\"} - - cd $WORKSPACE - ## Setup build folder if [ "${{ inputs.force-full-build }}" == "true" ] && [ -d $WORKSPACE/build ]; then rm -rf $WORKSPACE/build @@ -313,13 +286,11 @@ jobs: DOCKER_SRC_DIR="/workspace/$(realpath --relative-to=$WORKSPACE $SRC_DIR)" DOCKER_BUILD_DIR="/workspace/$(realpath --relative-to=$WORKSPACE $BUILD_DIR)" DOCKER_CI_DIR="/workspace/$(realpath --relative-to=$WORKSPACE $CI_DIR)" - DOCKER_REGRESSION_DIR="/workspace/$(realpath --relative-to=$WORKSPACE $REGRESSION_DIR)" DOCKER_LOG_DIR="/workspace/$(realpath --relative-to=$WORKSPACE ${{ env.LOG_DIR }})" echo "DOCKER_SRC_DIR=$DOCKER_SRC_DIR" >> $GITHUB_ENV echo "DOCKER_BUILD_DIR=$DOCKER_BUILD_DIR" >> $GITHUB_ENV echo "DOCKER_CI_DIR=$DOCKER_CI_DIR" >> $GITHUB_ENV - echo "DOCKER_REGRESSION_DIR=$DOCKER_REGRESSION_DIR" >> $GITHUB_ENV echo "DOCKER_LOG_DIR=$DOCKER_LOG_DIR" >> $GITHUB_ENV export XDG_CACHE_HOME="/cache" @@ -349,24 +320,17 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env; \${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir ${DOCKER_BUILD_DIR} --results-dir \${RESULTS_DIR}/unit -j \${VM_MAX_PARALLEL_TESTS}" + /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} UNIT" else echo "Launching unit test suite." - . ${CI_DIR}/scripts/setup-test-env.sh "${BUILD_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" - env - ${VM_PYTHON3_EXECUTABLE} ${CI_DIR}/scripts/tests/sofa_unit_tests.py --build-dir "${BUILD_DIR}" --results-dir "${RESULTS_DIR}/unit" -j ${VM_MAX_PARALLEL_TESTS} + bash ${CI_DIR}/scripts/test.sh "${BUILD_DIR}" "${SRC_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" "UNIT" fi - if [[ ! "$(cd "${{ env.BUILD_DIR }}/tests_results/unit" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then + if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -maxdepth 1 -type f)" == *"unit-tests_"* ]]; then exit 1 - else - if [[ "$(awk -F= '$1=="crashes" {print $2}' ${{ env.BUILD_DIR }}/tests_results/unit/summary.txt)" != '0' || "$(awk -F= '$1=="failures" {print $2}' ${{ env.BUILD_DIR }}/tests_results/unit/summary.txt)" != "0" ]]; then - exit 1 - fi fi - - name: Scene tests id: scene-tests-step if: always() && steps.build-step.outcome == 'success' && inputs.generate-binaries == false && inputs.with-all-tests == true @@ -380,21 +344,15 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "cd /workspace; . ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; \${VM_PYTHON3_EXECUTABLE} ${DOCKER_CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${DOCKER_SRC_DIR}" --build-dir \"${DOCKER_BUILD_DIR}\" --results-dir \"\${RESULTS_DIR}/scene\" -j \${VM_MAX_PARALLEL_TESTS}" + /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} SCENE" else echo "Launching scene test suite." - . ${CI_DIR}/scripts/setup-test-env.sh "${BUILD_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" - env - ${VM_PYTHON3_EXECUTABLE} ${CI_DIR}/scripts/tests/sofa_scene_tests.py --src-dir "${SRC_DIR}" --build-dir "${BUILD_DIR}" --results-dir "${RESULTS_DIR}/scene" -j ${VM_MAX_PARALLEL_TESTS} + bash ${CI_DIR}/scripts/test.sh "${BUILD_DIR}" "${SRC_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" "SCENE" fi - if [[ ! "$(cd "${{ env.BUILD_DIR }}/tests_results/scene" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then + if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -maxdepth 1 -type f)" == *"scene-tests_"* ]]; then exit 1 - else - if [[ "$(awk -F= '$1=="crashes" {print $2}' ${{ env.BUILD_DIR }}/tests_results/scene/summary.txt)" != '0' || "$(awk -F= '$1=="failures" {print $2}' ${{ env.BUILD_DIR }}/tests_results/scene/summary.txt)" != "0" ]]; then - exit 1 - fi fi - name: Regression tests @@ -410,21 +368,15 @@ jobs: docker run --rm \ --user $(id -u):$(id -g) --network=host -v $WORKSPACE:/workspace \ ${DOCKER_IMAGE} \ - /bin/bash -c "export REGRESSION_DIR="$DOCKER_REGRESSION_DIR"; cd /workspace;. ${DOCKER_CI_DIR}/scripts/setup-test-env.sh \"${DOCKER_BUILD_DIR}\" \"${DOCKER_CI_DIR}/scripts/\" \"${NODE_NAME}\" \"${{ inputs.python-version }}\"; env ; \${VM_PYTHON3_EXECUTABLE} ${DOCKER_REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${DOCKER_SRC_DIR}/examples" --input "${DOCKER_SRC_DIR}/applications" --input "${DOCKER_BUILD_DIR}/external_directories/fetched" --output-logs-errors "\${RESULTS_DIR}/regression" --legacy-regression --jobs \${VM_MAX_PARALLEL_TESTS} " + /bin/bash -c "env ; cd /workspace; /bin/bash $DOCKER_CI_DIR/scripts/test.sh $DOCKER_BUILD_DIR $DOCKER_SRC_DIR $DOCKER_CI_DIR/scripts/ ${NODE_NAME} ${{ inputs.python-version }} REGRESSION" else echo "Launching regression test suite" - . ${CI_DIR}/scripts/setup-test-env.sh "${BUILD_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" - env - ${VM_PYTHON3_EXECUTABLE} ${REGRESSION_DIR}/SofaRegressionProgram/SofaRegressionProgram.py --input "${SRC_DIR}/examples" --input "${SRC_DIR}/applications" --input "${BUILD_DIR}/external_directories/fetched" --output-logs-errors "${RESULTS_DIR}/regression" --legacy-regression -j ${VM_MAX_PARALLEL_TESTS} + bash ${CI_DIR}/scripts/test.sh "${BUILD_DIR}" "${SRC_DIR}" "${CI_DIR}/scripts/" "${NODE_NAME}" "${{ inputs.python-version }}" "REGRESSION" fi - if [[ ! "$(cd "${{ env.BUILD_DIR }}/tests_results/regression" && find . -maxdepth 1 -type f)" == *"summary"* ]]; then - exit 1 - else - if [[ "$(awk -F= '$1=="crashes" {print $2}' ${{ env.BUILD_DIR }}/tests_results/regression/summary.txt)" != '0' || "$(awk -F= '$1=="failures" {print $2}' ${{ env.BUILD_DIR }}/tests_results/regression/summary.txt)" != "0" ]]; then - exit 1 - fi + if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -maxdepth 1 -type f)" == *"regression-tests_"* ]]; then + exit 1 fi @@ -481,7 +433,7 @@ jobs: fi if [[ "${{ inputs.generate-binaries }}" == "false" ]]; then - if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -mindepth 2 -maxdepth 2 -type f -name 'summary.txt')" != "" ]]; then + if [[ "$(cd "${{ env.BUILD_DIR }}/tests_results/" && find . -maxdepth 1 -type f)" != "" ]]; then echo "❌ Tests have resulted in : " echo "" python3 ${{ env.CI_DIR }}/scripts/generate-tests-table.py "${{ env.BUILD_DIR }}/tests_results/" @@ -491,18 +443,18 @@ jobs: echo "#----------------------------------------#" for testType in 'unit' 'scene' 'regression'; do - capitalized="$(echo "${testType:0:1}" | tr '[:lower:]' '[:upper:]')${testType:1}" - echo -e "${bold}${capitalized}:${normal}" for errorType in 'errors' 'crashes' 'failures'; do - if [ -f "${{ env.BUILD_DIR }}/tests_results/${testType}/${testType}_${errorType}.txt" ]; then + if [ -f "${{ env.BUILD_DIR }}/tests_results/${testType}-tests_${errorType}" ]; then + capitalized="$(echo "${testType:0:1}" | tr '[:lower:]' '[:upper:]')${testType:1}" + echo "" + echo -e "${bold}${capitalized} ${errorType}:${normal}" echo "" - cat "${{ env.BUILD_DIR }}/tests_results/${testType}/${testType}_${errorType}.txt" + cat "${{ env.BUILD_DIR }}/tests_results/${testType}-tests_${errorType}" echo "" + echo "#----------------------------------------#" fi done - echo "#----------------------------------------#" - echo "" done echo -e "${bold}You can download all logs here : ${{ steps.publish-tests-logs.outputs.artifact-url }}${normal}" exit 1 diff --git a/.github/workflows/CI_trigger_build_and_tests.yml b/.github/workflows/CI_trigger_build_and_tests.yml index 430873c3f14..ebb9a7c2a03 100644 --- a/.github/workflows/CI_trigger_build_and_tests.yml +++ b/.github/workflows/CI_trigger_build_and_tests.yml @@ -231,7 +231,7 @@ jobs: build-on: needs: filter_build if: ${{ github.repository_owner == 'sofa-framework' && needs.filter_build.outputs.SH_BUILDER_OS != '[]' }} - uses: bakpaul/sofa/.github/workflows/CI_build_and_test.yml@26_09_update_ci_with_new_test_scripts_and_pixi_based_ci_for_windows + uses: sofa-framework/sofa/.github/workflows/CI_build_and_test.yml@master with: sofa-branch-name: ${{ needs.filter_build.outputs.SOFA_BRANCH_NAME }} sofa-commit-sha: ${{ needs.filter_build.outputs.SOFA_COMMIT_SHA }} From 38a773eff92bcd47739a59ec34055d0af7d788d0 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Mon, 28 Sep 2026 10:18:37 +0200 Subject: [PATCH 21/26] Force the ci working branch unit UNIX CI follows --- .../workflows/CI_macos_linux_windows_pixi.yml | 28 +++++++++++++------ 1 file changed, 19 insertions(+), 9 deletions(-) diff --git a/.github/workflows/CI_macos_linux_windows_pixi.yml b/.github/workflows/CI_macos_linux_windows_pixi.yml index ce9ae585970..32a9fda687b 100644 --- a/.github/workflows/CI_macos_linux_windows_pixi.yml +++ b/.github/workflows/CI_macos_linux_windows_pixi.yml @@ -134,17 +134,27 @@ jobs: cd $WORKSPACE ## Clone CI and use ci-depends-on structure - ci_branch=${{ inputs.sofa-branch-name }} - ci_repo_url="https://www.github.com/sofa-framework/ci" + echo "\033[33mWARNING, the ci repository is currently forced on bakpaul:26_09_final_jenkins_2_github_migration, delete the lines marked as \"TO DELETE\" and uncomment the ones marked as \"TO UNCOMMENT\" to go back into a normal behavior.\033[0m" + ### TO DELETE ### + ci_branch=26_09_final_jenkins_2_github_migration + ci_repo_url="https://www.github.com/bakpaul/ci" + ### TO DELETE ### + + ### TO UNCOMMENT ### + #ci_branch=${{ inputs.sofa-branch-name }} + #ci_repo_url="https://www.github.com/sofa-framework/ci" + + + ## check if ci has a ci-depends-on + #ci_ci_depends_on=$(echo "${{ inputs.ci-depends-on }}" | jq .ci) + #if [ -n "${{ inputs.ci-depends-on }}" ] && [ "$ci_ci_depends_on" != "null" ]; then + # echo "ci-depends-on for ci repository detected." + # ci_repo_url=$(echo "${{ inputs.ci-depends-on }}" | jq .ci.repo_url) + # ci_branch=$(echo "${{ inputs.ci-depends-on }}" | jq .ci.branch_name) + #fi + ### TO UNCOMMENT ### - # check if ci has a ci-depends-on - ci_ci_depends_on=$(echo "${{ inputs.ci-depends-on }}" | jq .ci) - if [ -n "${{ inputs.ci-depends-on }}" ] && [ "$ci_ci_depends_on" != "null" ]; then - echo "ci-depends-on for ci repository detected." - ci_repo_url=$(echo "${{ inputs.ci-depends-on }}" | jq .ci.repo_url) - ci_branch=$(echo "${{ inputs.ci-depends-on }}" | jq .ci.branch_name) - fi echo "CI_BRANCH=$ci_branch" >> $GITHUB_ENV From a4328ec713b02503112b755446ecbe1f3e84ce79 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Mon, 28 Sep 2026 11:26:24 +0200 Subject: [PATCH 22/26] Base tests on powershell --- .../workflows/CI_macos_linux_windows_pixi.yml | 139 +++++++++++------- 1 file changed, 82 insertions(+), 57 deletions(-) diff --git a/.github/workflows/CI_macos_linux_windows_pixi.yml b/.github/workflows/CI_macos_linux_windows_pixi.yml index 32a9fda687b..25b17ceed24 100644 --- a/.github/workflows/CI_macos_linux_windows_pixi.yml +++ b/.github/workflows/CI_macos_linux_windows_pixi.yml @@ -260,6 +260,12 @@ jobs: if: always() && ${{ runner.os == 'Windows' }} run: | cd ${SRC_DIR} + + echo "Adding runtime related dependencies" + pixi add $(cat ${CI_DIR}/docker/python_extra_dependencies.txt) + pixi install -e ${{ inputs.preset }} + + echo "Refactoring environement variables to jump into powershell" PIXI_PREFIX="$(pwd -W)/.pixi/envs/${{ inputs.preset }}/" echo "VM_PYTHON3_EXECUTABLE=$PIXI_PREFIX/python.exe" >> $GITHUB_ENV echo "PIXI_PREFIX=$PIXI_PREFIX" >> $GITHUB_ENV @@ -296,86 +302,105 @@ jobs: - name: Unit tests id: unit-tests-step if: always() && runner.os == 'Windows' && steps.build-step.outcome == 'success' && inputs.generate-binaries == false - shell: cmd + shell: pwsh run: | - cd /d "%SRC_DIR%" + Set-Location $env:SRC_DIR - set "UNIT_RESULTS_DIR=%BUILD_DIR%\tests_results\unit" + $UnitResultsDir = Join-Path $env:BUILD_DIR "tests_results\unit" + $env:UNIT_RESULTS_DIR = $UnitResultsDir # in case the script or child processes need it - REM Activate the environment in the terminal - pixi shell-hook --shell cmd -e ${{ inputs.preset }} > "%TEMP%\pixi_hook.bat" - call "%TEMP%\pixi_hook.bat" - del "%TEMP%\pixi_hook.bat" + # Activate the environment in the terminal + pixi shell-hook --shell powershell -e ${{ inputs.preset }} | Out-String | Invoke-Expression - python %CI_DIR%\scripts\tests\sofa_unit_tests.py --build-dir "%BUILD_DIR%" --results-dir "%UNIT_RESULTS_DIR%" -j %VM_MAX_PARALLEL_TESTS% + python "$env:CI_DIR\scripts\tests\sofa_unit_tests.py" ` + --build-dir "$env:BUILD_DIR" ` + --results-dir "$UnitResultsDir" ` + -j $env:VM_MAX_PARALLEL_TESTS - if not exist "%UNIT_RESULTS_DIR%\*summary*" exit /b 1 + if (-not (Test-Path "$UnitResultsDir\*summary*")) { exit 1 } - set "CRASHES=" - set "FAILURES=" - for /f "usebackq tokens=1,2 delims==" %%a in ("%UNIT_RESULTS_DIR%\summary.txt") do ( - if "%%a"=="crashes" set "CRASHES=%%b" - if "%%a"=="failures" set "FAILURES=%%b" - ) + $crashes = $null + $failures = $null + foreach ($line in Get-Content "$UnitResultsDir\summary.txt") { + $key, $value = $line -split '=', 2 + switch ($key) { + 'crashes' { $crashes = $value } + 'failures' { $failures = $value } + } + } - if not "%CRASHES%"=="0" exit /b 1 - if not "%FAILURES%"=="0" exit /b 1 + if ($crashes -ne '0') { exit 1 } + if ($failures -ne '0') { exit 1 } - name: Scene tests id: scene-tests-step if: always() && runner.os == 'Windows' && steps.build-step.outcome == 'success' && inputs.generate-binaries == false && inputs.with-all-tests == true - shell: cmd + shell: pwsh run: | - cd /d "%SRC_DIR%" + Set-Location $env:SRC_DIR - set "SCENE_RESULTS_DIR=%BUILD_DIR%\tests_results\scene" + $SceneResultsDir = Join-Path $env:BUILD_DIR "tests_results\scene" + $env:SCENE_RESULTS_DIR = $SceneResultsDir # in case the script or child processes need it - REM Activate the environment in the terminal - pixi shell-hook --shell cmd -e ${{ inputs.preset }} > "%TEMP%\pixi_hook.bat" - call "%TEMP%\pixi_hook.bat" - del "%TEMP%\pixi_hook.bat" + # Activate the environment in the terminal + pixi shell-hook --shell powershell -e ${{ inputs.preset }} | Out-String | Invoke-Expression - python %CI_DIR%\scripts\tests\sofa_scene_tests.py --src-dir "%SRC_DIR%" --build-dir "%BUILD_DIR%" --results-dir "%SCENE_RESULTS_DIR%" -j %VM_MAX_PARALLEL_TESTS% + python "$env:CI_DIR\scripts\tests\sofa_scene_tests.py" ` + --src-dir "$env:SRC_DIR" ` + --build-dir "$env:BUILD_DIR" ` + --results-dir "$SceneResultsDir" ` + -j $env:VM_MAX_PARALLEL_TESTS - if not exist "%SCENE_RESULTS_DIR%\*summary*" exit /b 1 + if (-not (Test-Path "$SceneResultsDir\*summary*")) { exit 1 } - set "CRASHES=" - set "FAILURES=" - for /f "usebackq tokens=1,2 delims==" %%a in ("%SCENE_RESULTS_DIR%\summary.txt") do ( - if "%%a"=="crashes" set "CRASHES=%%b" - if "%%a"=="failures" set "FAILURES=%%b" - ) + $crashes = $null + $failures = $null + foreach ($line in Get-Content "$SceneResultsDir\summary.txt") { + $key, $value = $line -split '=', 2 + switch ($key) { + 'crashes' { $crashes = $value } + 'failures' { $failures = $value } + } + } - if not "%CRASHES%"=="0" exit /b 1 - if not "%FAILURES%"=="0" exit /b 1 + if ($crashes -ne '0') { exit 1 } + if ($failures -ne '0') { exit 1 } - name: Regression tests id: regression-tests-step if: always() && runner.os == 'Windows' && steps.build-step.outcome == 'success' && inputs.generate-binaries == false && inputs.with-all-tests == true - shell: cmd + shell: pwsh run: | - cd /d "%SRC_DIR%" - - set "REG_RESULTS_DIR=%BUILD_DIR%\tests_results\regression" - - REM Activate the environment in the terminal - pixi shell-hook --shell cmd -e ${{ inputs.preset }} > "%TEMP%\pixi_hook.bat" - call "%TEMP%\pixi_hook.bat" - del "%TEMP%\pixi_hook.bat" - - - python %REGRESSION_DIR%\SofaRegressionProgram\SofaRegressionProgram.py --input "%SRC_DIR%/examples" --input "%SRC_DIR%\applications" --input "%BUILD_DIR%\external_directories\fetched" --output-logs-errors "%REG_RESULTS_DIR%" --legacy-regression -j %VM_MAX_PARALLEL_TESTS% - if not exist "%REG_RESULTS_DIR%\*summary*" exit /b 1 - - set "CRASHES=" - set "FAILURES=" - for /f "usebackq tokens=1,2 delims==" %%a in ("%REG_RESULTS_DIR%\summary.txt") do ( - if "%%a"=="crashes" set "CRASHES=%%b" - if "%%a"=="failures" set "FAILURES=%%b" - ) - - if not "%CRASHES%"=="0" exit /b 1 - if not "%FAILURES%"=="0" exit /b 1 + Set-Location $env:SRC_DIR + + $RegResultsDir = Join-Path $env:BUILD_DIR "tests_results\regression" + $env:REG_RESULTS_DIR = $RegResultsDir # in case the script or child processes need it + + # Activate the environment in the terminal + pixi shell-hook --shell powershell -e ${{ inputs.preset }} | Out-String | Invoke-Expression + + python "$env:REGRESSION_DIR\SofaRegressionProgram\SofaRegressionProgram.py" ` + --input "$env:SRC_DIR/examples" ` + --input "$env:SRC_DIR\applications" ` + --input "$env:BUILD_DIR\external_directories\fetched" ` + --output-logs-errors "$RegResultsDir" ` + --legacy-regression ` + -j $env:VM_MAX_PARALLEL_TESTS + + if (-not (Test-Path "$RegResultsDir\*summary*")) { exit 1 } + + $crashes = $null + $failures = $null + foreach ($line in Get-Content "$RegResultsDir\summary.txt") { + $key, $value = $line -split '=', 2 + switch ($key) { + 'crashes' { $crashes = $value } + 'failures' { $failures = $value } + } + } + + if ($crashes -ne '0') { exit 1 } + if ($failures -ne '0') { exit 1 } - name: Publish artifacts From eb1e0c13ac262069df2e50ce59d55b08170ea596 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Mon, 28 Sep 2026 14:17:15 +0200 Subject: [PATCH 23/26] Fix remaining CUDA scene launched --- applications/plugins/SofaCUDA/examples/.scene-tests | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/applications/plugins/SofaCUDA/examples/.scene-tests b/applications/plugins/SofaCUDA/examples/.scene-tests index b2dde060046..cb5fb7f685f 100644 --- a/applications/plugins/SofaCUDA/examples/.scene-tests +++ b/applications/plugins/SofaCUDA/examples/.scene-tests @@ -47,6 +47,6 @@ ignore "ElementFEMForcefield/CudaLinearSmallStrainFEMForceField_tetra.scn" ignore "ElementFEMForcefield/CudaLinearSmallStrainFEMForceField_triangle.scn" ignore "ElementFEMForcefield/CudaLinearSmallStrainFEMForceField_prism.scn" ignore "ElementFEMForcefield/CudaLinearSmallStrainFEMForceField_pyramid.scn" -ignore "cpu-gpu_validation/CorotationalFEMForceField_tetra_cpu_gpu.scn" -ignore "benchmarks/Tetrahedron_corotational.py" -ignore "benchmarks/Hexahedron_corotational.py" +ignore "ElementFEMForcefield/cpu-gpu_validation/CorotationalFEMForceField_tetra_cpu_gpu.scn" +ignore "ElementFEMForcefield/benchmarks/Tetrahedron_corotational.py" +ignore "ElementFEMForcefield/benchmarks/Hexahedron_corotational.py" From aa458c87d47513b1f90140a4ed7a3a8370d9d40e Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Mon, 28 Sep 2026 15:12:14 +0200 Subject: [PATCH 24/26] Skip PrecomputedConstraintCorrection in scene tests as they are launched by the regression tests and the scene test make the aciton crash --- examples/.scene-tests | 3 +++ 1 file changed, 3 insertions(+) diff --git a/examples/.scene-tests b/examples/.scene-tests index 7578544b692..ce795d51776 100644 --- a/examples/.scene-tests +++ b/examples/.scene-tests @@ -50,3 +50,6 @@ ignore "Benchmark/Performance/Bar16-fem-implicit-CudaVec3f.py" ignore "Benchmark/Performance/Bar16-spring-rk4-CudaVec3d.py" ignore "Benchmark/Performance/Bar16-spring-rk4-CudaVec3f.py" + +# Crash on windows +ignore "Component/Constraint/Lagrangian/PrecomputedConstraintCorrection.scn" From 2c3cd11eaf5eca4c347cae324956435c33e2a211 Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Mon, 28 Sep 2026 15:14:56 +0200 Subject: [PATCH 25/26] Fix warning --- .github/workflows/CI_macos_linux_windows_pixi.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/CI_macos_linux_windows_pixi.yml b/.github/workflows/CI_macos_linux_windows_pixi.yml index 25b17ceed24..5dd5d0db5b6 100644 --- a/.github/workflows/CI_macos_linux_windows_pixi.yml +++ b/.github/workflows/CI_macos_linux_windows_pixi.yml @@ -257,7 +257,7 @@ jobs: - name: Setup env for tests shell: bash - if: always() && ${{ runner.os == 'Windows' }} + if: always() && runner.os == 'Windows' run: | cd ${SRC_DIR} From 2fcaae6bc95a9d68d9b4c1209419ae2e2f81917a Mon Sep 17 00:00:00 2001 From: Paul Baksic Date: Mon, 28 Sep 2026 19:44:13 +0200 Subject: [PATCH 26/26] TO REVERT, pass verbose to 2 for regression --- .github/workflows/CI_macos_linux_windows_pixi.yml | 1 + 1 file changed, 1 insertion(+) diff --git a/.github/workflows/CI_macos_linux_windows_pixi.yml b/.github/workflows/CI_macos_linux_windows_pixi.yml index 5dd5d0db5b6..6a48aeb7df7 100644 --- a/.github/workflows/CI_macos_linux_windows_pixi.yml +++ b/.github/workflows/CI_macos_linux_windows_pixi.yml @@ -385,6 +385,7 @@ jobs: --input "$env:BUILD_DIR\external_directories\fetched" ` --output-logs-errors "$RegResultsDir" ` --legacy-regression ` + --verbose 2 ` -j $env:VM_MAX_PARALLEL_TESTS if (-not (Test-Path "$RegResultsDir\*summary*")) { exit 1 }