Skip to content

fix: improve CI resilience for gradle wrapper download and DataNode #251

fix: improve CI resilience for gradle wrapper download and DataNode

fix: improve CI resilience for gradle wrapper download and DataNode #251

Workflow file for this run

# --------------------------------------------------------------------
#
# Licensed to the Apache Software Foundation (ASF) under one or more
# contributor license agreements. See the NOTICE file distributed
# with this work for additional information regarding copyright
# ownership. The ASF licenses this file to You under the Apache
# License, Version 2.0 (the "License"); you may not use this file
# except in compliance with the License. You may obtain a copy of the
# License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or
# implied. See the License for the specific language governing
# permissions and limitations under the License.
#
# --------------------------------------------------------------------
# Apache Cloudberry PXF CI Workflow
# --------------------------------------------------------------------
name: PXF CI Pipeline
on:
push:
branches: [ main ]
pull_request:
types: [opened, synchronize, reopened, edited]
workflow_dispatch:
permissions:
contents: read
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: ${{ github.ref != 'refs/heads/main' }}
env:
JAVA_VERSION: "11"
JAVA_HOME: "/usr/lib/jvm/java-11-openjdk"
GO_VERSION: "1.21"
GPHOME: "/usr/local/cloudberry-db"
CLOUDBERRY_VERSION: "main"
PXF_HOME: "/usr/local/pxf"
jobs:
# Stage 1: Build artifacts (runs in parallel)
build-cloudberry-deb:
name: Build Cloudberry DEB Package
runs-on: ubuntu-latest
container:
image: apache/incubator-cloudberry:cbdb-build-ubuntu22.04-latest
options: --user root
steps:
- name: Checkout Cloudberry source
uses: actions/checkout@v4
with:
repository: apache/cloudberry
ref: ${{ env.CLOUDBERRY_VERSION }}
path: workspace/cloudberry
submodules: true
- name: Checkout PXF source (for build script)
uses: actions/checkout@v4
with:
path: cloudberry-pxf
- name: Build Cloudberry DEB
run: |
export WORKSPACE=$PWD/workspace
export CLOUDBERRY_VERSION=99.0.0
export CLOUDBERRY_BUILD=1
bash cloudberry-pxf/ci/docker/pxf-cbdb-dev/ubuntu/script/build_cloudberry_deb.sh
- name: Package Cloudberry source
run: |
cd workspace
tar czf cloudberry-source.tar.gz cloudberry/
- name: Upload DEB artifact
uses: actions/upload-artifact@v4
with:
name: cloudberry-deb
path: workspace/cloudberry-deb/*.deb
retention-days: 7
- name: Upload Cloudberry source artifact
uses: actions/upload-artifact@v4
with:
name: cloudberry-source
path: workspace/cloudberry-source.tar.gz
retention-days: 7
build-cloudberry-rpm:
name: Build Cloudberry RPM Package
runs-on: ubuntu-latest
container:
image: apache/incubator-cloudberry:cbdb-build-rocky9-latest
options: --user root
steps:
- name: Checkout Cloudberry source
uses: actions/checkout@v4
with:
repository: apache/cloudberry
ref: ${{ env.CLOUDBERRY_VERSION }}
path: workspace/cloudberry
submodules: true
- name: Checkout PXF source (for build script)
uses: actions/checkout@v4
with:
path: cloudberry-pxf
- name: Build Cloudberry RPM
run: |
export WORKSPACE=$PWD/workspace
export CLOUDBERRY_VERSION=99.0.0
export CLOUDBERRY_BUILD=1
bash cloudberry-pxf/ci/docker/pxf-cbdb-dev/rocky9/script/build_cloudberry_rpm.sh
- name: Package Cloudberry source
run: |
cd workspace
tar czf cloudberry-source-rocky9.tar.gz cloudberry/
- name: Upload RPM artifact
uses: actions/upload-artifact@v4
with:
name: cloudberry-rpm
path: workspace/cloudberry-rpm/*.rpm
retention-days: 7
- name: Upload Cloudberry source artifact (Rocky 9)
uses: actions/upload-artifact@v4
with:
name: cloudberry-source-rocky9
path: workspace/cloudberry-source-rocky9.tar.gz
retention-days: 7
build-docker-images:
name: Build Docker Images (Ubuntu)
runs-on: ubuntu-latest
steps:
- name: Checkout PXF source
uses: actions/checkout@v4
with:
path: cloudberry-pxf
- name: Cache singlecluster image
id: cache-image
uses: actions/cache@v4
with:
path: /tmp/singlecluster-image.tar
key: singlecluster-ubuntu-${{ hashFiles('ci/singlecluster/**') }}
- name: Build singlecluster image
if: steps.cache-image.outputs.cache-hit != 'true'
run: |
cd cloudberry-pxf/ci/singlecluster
docker build -t pxf/singlecluster:3 .
docker save pxf/singlecluster:3 > /tmp/singlecluster-image.tar
- name: Upload singlecluster image
uses: actions/upload-artifact@v4
with:
name: singlecluster-image
path: /tmp/singlecluster-image.tar
retention-days: 1
java-compatibility-test:
name: build-and-test with java v${{ matrix.java }}
runs-on: ubuntu-latest
strategy:
matrix:
java: [ '8', '11', '17' ]
fail-fast: false
steps:
- uses: actions/checkout@v4
- uses: actions/setup-java@v4
with:
java-version: ${{ matrix.java }}
distribution: 'corretto'
- name: Assemble and test with Gradle
working-directory: ./server
run: make test
build-docker-images-rocky9:
name: Build Docker Images (Rocky 9)
runs-on: ubuntu-latest
steps:
- name: Checkout PXF source
uses: actions/checkout@v4
with:
path: cloudberry-pxf
- name: Cache singlecluster Rocky 9 image
id: cache-image-rocky9
uses: actions/cache@v4
with:
path: /tmp/singlecluster-rocky9-image.tar
key: singlecluster-rocky9-${{ hashFiles('ci/singlecluster/**') }}
- name: Build singlecluster Rocky 9 image
if: steps.cache-image-rocky9.outputs.cache-hit != 'true'
run: |
cd cloudberry-pxf/ci/singlecluster
docker build --build-arg BASE_IMAGE=apache/incubator-cloudberry:cbdb-build-rocky9-latest -t pxf/singlecluster-rocky9:3 .
docker save pxf/singlecluster-rocky9:3 > /tmp/singlecluster-rocky9-image.tar
- name: Upload singlecluster Rocky 9 image
uses: actions/upload-artifact@v4
with:
name: singlecluster-rocky9-image
path: /tmp/singlecluster-rocky9-image.tar
retention-days: 1
# Stage 1.5: Build test-ready images (Cloudberry + packages pre-installed)
build-test-image:
name: Build Test-Ready Image (Ubuntu)
needs: [build-cloudberry-deb, build-docker-images]
runs-on: ubuntu-latest
steps:
- name: Checkout PXF source
uses: actions/checkout@v4
with:
path: cloudberry-pxf
- name: Download singlecluster image
uses: actions/download-artifact@v4
with:
name: singlecluster-image
path: /tmp
- name: Download Cloudberry DEB
uses: actions/download-artifact@v4
with:
name: cloudberry-deb
path: cloudberry-pxf/ci/docker/pxf-cbdb-dev/ubuntu/cloudberry-package/
- name: Download Cloudberry source
uses: actions/download-artifact@v4
with:
name: cloudberry-source
path: /tmp
- name: Prepare build context
run: |
docker load < /tmp/singlecluster-image.tar
mkdir -p cloudberry-pxf/ci/docker/pxf-cbdb-dev/ubuntu/cloudberry-source
tar xzf /tmp/cloudberry-source.tar.gz --strip-components=1 -C cloudberry-pxf/ci/docker/pxf-cbdb-dev/ubuntu/cloudberry-source/
ls cloudberry-pxf/ci/docker/pxf-cbdb-dev/ubuntu/cloudberry-package/
ls cloudberry-pxf/ci/docker/pxf-cbdb-dev/ubuntu/cloudberry-source/Makefile
- name: Build test-ready image
run: |
cd cloudberry-pxf/ci/docker/pxf-cbdb-dev/ubuntu
docker build -f Dockerfile.test-ready -t pxf/test-ready-ubuntu:latest .
docker save pxf/test-ready-ubuntu:latest > /tmp/test-ready-ubuntu.tar
- name: Upload test-ready image
uses: actions/upload-artifact@v4
with:
name: test-ready-ubuntu-image
path: /tmp/test-ready-ubuntu.tar
retention-days: 1
build-test-image-rocky9:
name: Build Test-Ready Image (Rocky 9)
needs: [build-cloudberry-rpm, build-docker-images-rocky9]
runs-on: ubuntu-latest
steps:
- name: Checkout PXF source
uses: actions/checkout@v4
with:
path: cloudberry-pxf
- name: Download singlecluster Rocky 9 image
uses: actions/download-artifact@v4
with:
name: singlecluster-rocky9-image
path: /tmp
- name: Download Cloudberry RPM
uses: actions/download-artifact@v4
with:
name: cloudberry-rpm
path: cloudberry-pxf/ci/docker/pxf-cbdb-dev/rocky9/cloudberry-package/
- name: Download Cloudberry source (Rocky 9)
uses: actions/download-artifact@v4
with:
name: cloudberry-source-rocky9
path: /tmp
- name: Prepare build context
run: |
docker load < /tmp/singlecluster-rocky9-image.tar
mkdir -p cloudberry-pxf/ci/docker/pxf-cbdb-dev/rocky9/cloudberry-source
tar xzf /tmp/cloudberry-source-rocky9.tar.gz --strip-components=1 -C cloudberry-pxf/ci/docker/pxf-cbdb-dev/rocky9/cloudberry-source/
ls cloudberry-pxf/ci/docker/pxf-cbdb-dev/rocky9/cloudberry-package/
ls cloudberry-pxf/ci/docker/pxf-cbdb-dev/rocky9/cloudberry-source/Makefile
- name: Build test-ready image
run: |
cd cloudberry-pxf/ci/docker/pxf-cbdb-dev/rocky9
docker build -f Dockerfile.test-ready -t pxf/test-ready-rocky9:latest .
docker save pxf/test-ready-rocky9:latest > /tmp/test-ready-rocky9.tar
- name: Upload test-ready image
uses: actions/upload-artifact@v4
with:
name: test-ready-rocky9-image
path: /tmp/test-ready-rocky9.tar
retention-days: 1
# Stage 2: Parallel test jobs using matrix strategy
pxf-test:
name: Test PXF - ${{ matrix.test_group }}
needs: [build-test-image]
runs-on: ubuntu-latest
strategy:
fail-fast: false
matrix:
test_group:
- cli
- external-table
- fdw
- sanity
- smoke
- hdfs
- hcatalog
- hcfs
- hive
- hbase
- profile
- jdbc
- proxy
- unused
- s3
- features
- gpdb
- gpdb_fdw
- load
- pxf_extension
steps:
- name: Free disk space
run: |
sudo rm -rf /usr/share/dotnet
sudo rm -rf /opt/ghc
sudo rm -rf /usr/local/share/boost
sudo rm -rf /usr/local/lib/android
sudo rm -rf /opt/hostedtoolcache
sudo docker system prune -af
df -h
- name: Checkout PXF source
uses: actions/checkout@v4
with:
fetch-depth: 1
path: cloudberry-pxf
submodules: true
- name: Download test-ready image
uses: actions/download-artifact@v4
with:
name: test-ready-ubuntu-image
path: /tmp
- name: Load test-ready image
run: docker load < /tmp/test-ready-ubuntu.tar
- name: Start Services
id: start_services
run: |
cd cloudberry-pxf
docker compose -f ci/docker/pxf-cbdb-dev/ubuntu/docker-compose.yml down -v || true
docker compose -f ci/docker/pxf-cbdb-dev/ubuntu/docker-compose.yml up -d
docker exec pxf-cbdb-dev bash -lc "cd /home/gpadmin/workspace/cloudberry-pxf && ./ci/docker/pxf-cbdb-dev/common/script/entrypoint_fast.sh"
- name: Run Test - ${{ matrix.test_group }}
id: run_test
continue-on-error: true
timeout-minutes: 120
run: |
docker exec pxf-cbdb-dev bash -lc "cd /home/gpadmin/workspace/cloudberry-pxf/automation && source ../ci/docker/pxf-cbdb-dev/common/script/pxf-env.sh && ../ci/docker/pxf-cbdb-dev/common/script/run_tests.sh ${{ matrix.test_group }}"
- name: Collect artifacts and generate stats
if: always()
id: collect_artifacts
run: |
mkdir -p artifacts/logs
TEST_GROUP="${{ matrix.test_group }}"
TEST_RESULT="${{ steps.run_test.outcome }}"
# Initialize counters
TOTAL=0
PASSED=0
FAILED=0
SKIPPED=0
# Copy test artifacts
cp -r cloudberry-pxf/automation/test_artifacts/* artifacts/ 2>/dev/null || true
docker exec pxf-cbdb-dev bash -c "cp -r /usr/local/pxf/logs/* /tmp/pxf-logs/ 2>/dev/null || true" || true
docker cp pxf-cbdb-dev:/tmp/pxf-logs artifacts/logs/ 2>/dev/null || true
# Parse surefire reports for automation tests
if [[ "$TEST_GROUP" != "cli" && "$TEST_GROUP" != "server" ]]; then
for xml in cloudberry-pxf/automation/target/surefire-reports/TEST-*.xml; do
if [ -f "$xml" ]; then
tests=$(grep -oP 'tests="\K\d+' "$xml" 2>/dev/null | head -1 || echo "0")
failures=$(grep -oP 'failures="\K\d+' "$xml" 2>/dev/null | head -1 || echo "0")
errors=$(grep -oP 'errors="\K\d+' "$xml" 2>/dev/null | head -1 || echo "0")
skipped=$(grep -oP 'skipped="\K\d+' "$xml" 2>/dev/null | head -1 || echo "0")
TOTAL=$((TOTAL + tests))
FAILED=$((FAILED + failures + errors))
SKIPPED=$((SKIPPED + skipped))
fi
done
PASSED=$((TOTAL - FAILED - SKIPPED))
fi
# Generate stats JSON
cat > artifacts/test_stats.json <<EOF
{
"group": "$TEST_GROUP",
"result": "$TEST_RESULT",
"total": $TOTAL,
"passed": $PASSED,
"failed": $FAILED,
"skipped": $SKIPPED
}
EOF
echo "failed_count=$FAILED" >> $GITHUB_OUTPUT
echo "skipped_count=$SKIPPED" >> $GITHUB_OUTPUT
echo "Test stats for $TEST_GROUP: total=$TOTAL, passed=$PASSED, failed=$FAILED, skipped=$SKIPPED"
- name: Cleanup containers
if: always()
run: |
cd cloudberry-pxf
docker compose -f ci/docker/pxf-cbdb-dev/ubuntu/docker-compose.yml down -v || true
- name: Upload test artifacts
if: always()
uses: actions/upload-artifact@v4
with:
name: test-results-${{ matrix.test_group }}
path: artifacts/**
if-no-files-found: ignore
retention-days: 7
- name: Check test result
if: always()
run: |
FAILED_COUNT="${{ steps.collect_artifacts.outputs.failed_count || 0 }}"
SKIPPED_COUNT="${{ steps.collect_artifacts.outputs.skipped_count || 0 }}"
if [ "${{ steps.run_test.outcome }}" == "failure" ] || [ "${{ steps.run_test.outcome }}" == "skipped" ] || [ "$FAILED_COUNT" -gt 0 ]; then
echo "Test group ${{ matrix.test_group }} failed (outcome: ${{ steps.run_test.outcome }}, Failures: $FAILED_COUNT, Skipped: $SKIPPED_COUNT)"
exit 1
fi
# Stage 2b: Rocky 9 parallel test jobs
pxf-test-rocky9:
name: Test PXF Rocky9 - ${{ matrix.test_group }}
needs: [build-test-image-rocky9]
runs-on: ubuntu-latest
strategy:
fail-fast: false
matrix:
test_group:
- cli
- external-table
- fdw
- server
- sanity
- smoke
- hdfs
- hcatalog
- hcfs
- hive
- hbase
- profile
- jdbc
- proxy
- unused
- s3
- features
- gpdb
- gpdb_fdw
- load
- pxf_extension
steps:
- name: Free disk space
run: |
sudo rm -rf /usr/share/dotnet
sudo rm -rf /opt/ghc
sudo rm -rf /usr/local/share/boost
sudo rm -rf /usr/local/lib/android
sudo rm -rf /opt/hostedtoolcache
sudo docker system prune -af
df -h
- name: Checkout PXF source
uses: actions/checkout@v4
with:
fetch-depth: 1
path: cloudberry-pxf
submodules: true
- name: Download test-ready Rocky 9 image
uses: actions/download-artifact@v4
with:
name: test-ready-rocky9-image
path: /tmp
- name: Load test-ready Rocky 9 image
run: docker load < /tmp/test-ready-rocky9.tar
- name: Start Services
id: start_services
run: |
cd cloudberry-pxf
docker compose -f ci/docker/pxf-cbdb-dev/rocky9/docker-compose.yml down -v || true
docker compose -f ci/docker/pxf-cbdb-dev/rocky9/docker-compose.yml up -d
docker exec pxf-cbdb-dev bash -lc "cd /home/gpadmin/workspace/cloudberry-pxf && ./ci/docker/pxf-cbdb-dev/common/script/entrypoint_fast.sh"
- name: Run Test - ${{ matrix.test_group }}
id: run_test
continue-on-error: true
timeout-minutes: 120
run: |
docker exec pxf-cbdb-dev bash -lc "cd /home/gpadmin/workspace/cloudberry-pxf/automation && source ../ci/docker/pxf-cbdb-dev/common/script/pxf-env.sh && ../ci/docker/pxf-cbdb-dev/common/script/run_tests.sh ${{ matrix.test_group }}"
- name: Collect artifacts and generate stats
if: always()
id: collect_artifacts
run: |
mkdir -p artifacts/logs
TEST_GROUP="${{ matrix.test_group }}"
TEST_RESULT="${{ steps.run_test.outcome }}"
# Initialize counters
TOTAL=0
PASSED=0
FAILED=0
SKIPPED=0
# Copy test artifacts
cp -r cloudberry-pxf/automation/test_artifacts/* artifacts/ 2>/dev/null || true
docker exec pxf-cbdb-dev bash -c "cp -r /usr/local/pxf/logs/* /tmp/pxf-logs/ 2>/dev/null || true" || true
docker cp pxf-cbdb-dev:/tmp/pxf-logs artifacts/logs/ 2>/dev/null || true
# Parse surefire reports for automation tests
if [[ "$TEST_GROUP" != "cli" && "$TEST_GROUP" != "server" ]]; then
for xml in cloudberry-pxf/automation/target/surefire-reports/TEST-*.xml; do
if [ -f "$xml" ]; then
tests=$(grep -oP 'tests="\K\d+' "$xml" 2>/dev/null | head -1 || echo "0")
failures=$(grep -oP 'failures="\K\d+' "$xml" 2>/dev/null | head -1 || echo "0")
errors=$(grep -oP 'errors="\K\d+' "$xml" 2>/dev/null | head -1 || echo "0")
skipped=$(grep -oP 'skipped="\K\d+' "$xml" 2>/dev/null | head -1 || echo "0")
TOTAL=$((TOTAL + tests))
FAILED=$((FAILED + failures + errors))
SKIPPED=$((SKIPPED + skipped))
fi
done
PASSED=$((TOTAL - FAILED - SKIPPED))
fi
# Generate stats JSON
cat > artifacts/test_stats.json <<EOF
{
"group": "$TEST_GROUP",
"result": "$TEST_RESULT",
"total": $TOTAL,
"passed": $PASSED,
"failed": $FAILED,
"skipped": $SKIPPED
}
EOF
echo "failed_count=$FAILED" >> $GITHUB_OUTPUT
echo "skipped_count=$SKIPPED" >> $GITHUB_OUTPUT
echo "Test stats for $TEST_GROUP (Rocky 9): total=$TOTAL, passed=$PASSED, failed=$FAILED, skipped=$SKIPPED"
- name: Cleanup containers
if: always()
run: |
cd cloudberry-pxf
docker compose -f ci/docker/pxf-cbdb-dev/rocky9/docker-compose.yml down -v || true
- name: Upload test artifacts
if: always()
uses: actions/upload-artifact@v4
with:
name: test-results-rocky9-${{ matrix.test_group }}
path: artifacts/**
if-no-files-found: ignore
retention-days: 7
- name: Check test result
if: always()
run: |
FAILED_COUNT="${{ steps.collect_artifacts.outputs.failed_count || 0 }}"
SKIPPED_COUNT="${{ steps.collect_artifacts.outputs.skipped_count || 0 }}"
if [ "${{ steps.run_test.outcome }}" == "failure" ] || [ "${{ steps.run_test.outcome }}" == "skipped" ] || [ "$FAILED_COUNT" -gt 0 ]; then
echo "Test group ${{ matrix.test_group }} (Rocky 9) failed (outcome: ${{ steps.run_test.outcome }}, Failures: $FAILED_COUNT, Skipped: $SKIPPED_COUNT)"
exit 1
fi
# Stage 3: Summary job
test-summary:
name: Test Summary
needs: [pxf-test, pxf-test-rocky9]
if: always()
runs-on: ubuntu-latest
steps:
- name: Download all test artifacts
uses: actions/download-artifact@v4
with:
path: all-artifacts
pattern: test-results-*
- name: Generate summary
run: |
echo "## PXF Test Results Summary" >> $GITHUB_STEP_SUMMARY
echo "" >> $GITHUB_STEP_SUMMARY
generate_os_summary() {
local os_label="$1"
local pattern="$2"
# OS-level counters
local OVERALL_TOTAL=0
local OVERALL_PASSED=0
local OVERALL_FAILED=0
local OVERALL_SKIPPED=0
local GROUPS_PASSED=0
local GROUPS_FAILED=0
local FAILED_GROUP_NAMES=""
declare -A GROUP_STATS
for dir in all-artifacts/${pattern}; do
if [ -d "$dir" ] && [ -f "$dir/test_stats.json" ]; then
group=$(cat "$dir/test_stats.json" | grep -oP '"group":\s*"\K[^"]+' || basename "$dir" | sed "s/${pattern%\*}//")
result=$(cat "$dir/test_stats.json" | grep -oP '"result":\s*"\K[^"]+' || echo "unknown")
total=$(cat "$dir/test_stats.json" | grep -oP '"total":\s*\K\d+' || echo "0")
passed=$(cat "$dir/test_stats.json" | grep -oP '"passed":\s*\K\d+' || echo "0")
failed=$(cat "$dir/test_stats.json" | grep -oP '"failed":\s*\K\d+' || echo "0")
skipped=$(cat "$dir/test_stats.json" | grep -oP '"skipped":\s*\K\d+' || echo "0")
GROUP_STATS[$group]="$result,$total,$passed,$failed,$skipped"
OVERALL_TOTAL=$((OVERALL_TOTAL + total))
OVERALL_PASSED=$((OVERALL_PASSED + passed))
OVERALL_FAILED=$((OVERALL_FAILED + failed))
OVERALL_SKIPPED=$((OVERALL_SKIPPED + skipped))
if [ "$result" == "success" ] && [ "$failed" -eq 0 ]; then
GROUPS_PASSED=$((GROUPS_PASSED + 1))
else
GROUPS_FAILED=$((GROUPS_FAILED + 1))
FAILED_GROUP_NAMES="${FAILED_GROUP_NAMES}${group} "
fi
fi
done
echo "### ${os_label}" >> $GITHUB_STEP_SUMMARY
echo "" >> $GITHUB_STEP_SUMMARY
if [ $GROUPS_FAILED -eq 0 ]; then
echo "All ${GROUPS_PASSED} test groups passed" >> $GITHUB_STEP_SUMMARY
else
echo "${GROUPS_FAILED} of $((GROUPS_PASSED + GROUPS_FAILED)) test groups failed" >> $GITHUB_STEP_SUMMARY
fi
echo "" >> $GITHUB_STEP_SUMMARY
echo "- Total Tests: $OVERALL_TOTAL" >> $GITHUB_STEP_SUMMARY
echo "- Passed: $OVERALL_PASSED" >> $GITHUB_STEP_SUMMARY
echo "- Failed: $OVERALL_FAILED" >> $GITHUB_STEP_SUMMARY
echo "- Skipped: $OVERALL_SKIPPED" >> $GITHUB_STEP_SUMMARY
echo "" >> $GITHUB_STEP_SUMMARY
echo "| Test Group | Status | Passed | Failed | Skipped | Total |" >> $GITHUB_STEP_SUMMARY
echo "|------------|--------|-------:|-------:|--------:|------:|" >> $GITHUB_STEP_SUMMARY
for group in $(echo "${!GROUP_STATS[@]}" | tr ' ' '\n' | sort); do
IFS=',' read -r result total passed failed skipped <<< "${GROUP_STATS[$group]}"
if [ "$result" == "success" ] && [ "$failed" -eq 0 ]; then
status="PASS"
else
status="FAIL"
fi
echo "| $group | $status | $passed | $failed | $skipped | $total |" >> $GITHUB_STEP_SUMMARY
done
echo "" >> $GITHUB_STEP_SUMMARY
if [ $GROUPS_FAILED -gt 0 ]; then
echo "::error::${os_label}: ${GROUPS_FAILED} test group(s) failed: ${FAILED_GROUP_NAMES}"
return 1
fi
return 0
}
EXIT_CODE=0
# Ubuntu results (test-results-<group>, excluding test-results-rocky9-*)
generate_os_summary "Ubuntu 22.04" "test-results-[!r]*" || EXIT_CODE=1
# Rocky 9 results
generate_os_summary "Rocky 9" "test-results-rocky9-*" || EXIT_CODE=1
exit $EXIT_CODE