Skip to content

Commit bb8e48f

Browse files
committed
refactor: Use pytest JUnit XML for reliable test count parsing
Old approach: Parse text output with fragile sed regex - Fragile: '===== 43 passed in X.XXs =====' format could change - Complex: Greedy matching issues, cross-platform sed differences - Error-prone: Multiple patterns to maintain New approach: Use pytest --junitxml for structured output - Reliable: XML format is stable and documented - Simple: grep -oE extracts attributes directly - Standard: JUnit XML is pytest's native output format XML structure: <testsuite tests="43" failures="0" skipped="0"> Parsing: - tests=: Total tests run (passed + failed) - failures=: Failed tests - skipped=: Skipped tests - passed = tests - failures - skipped Benefits: - No regex fragility - Works on all platforms (grep -oE is POSIX) - More maintainable - Can add test result artifacts later
1 parent b1ac911 commit bb8e48f

1 file changed

Lines changed: 18 additions & 22 deletions

File tree

.github/workflows/test-python-bindings.yml

Lines changed: 18 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -203,41 +203,37 @@ jobs:
203203
cd bindings/python
204204
echo "🧪 Testing arcadedb-embedded (with bundled JRE)..."
205205
206-
# Run pytest with verbose output
207-
pytest tests/ -v --tb=short --color=yes 2>&1 | tee pytest-output.txt
208-
209-
# Check results
210-
if grep -q "failed" pytest-output.txt; then
211-
echo "❌ Tests FAILED"
212-
exit 1
213-
elif grep -q "passed" pytest-output.txt || grep -q "skipped" pytest-output.txt; then
214-
echo "✅ Tests PASSED"
215-
216-
# Count results (cross-platform: use sed instead of grep -P)
217-
# Format: "===== 43 passed, 2 skipped in 1.23s =====" or "===== 43 passed in 1.23s ====="
218-
# Use [^0-9] to match non-digit before number to avoid greedy matching
219-
PASSED=$(sed -n 's/.* \([0-9][0-9]*\) passed.*/\1/p' pytest-output.txt | tail -1)
220-
SKIPPED=$(sed -n 's/.* \([0-9][0-9]*\) skipped.*/\1/p' pytest-output.txt | tail -1)
221-
FAILED=$(sed -n 's/.* \([0-9][0-9]*\) failed.*/\1/p' pytest-output.txt | tail -1)
206+
# Run pytest with JUnit XML output for structured results
207+
set +e # Don't exit on test failures
208+
pytest tests/ -v --tb=short --color=yes --junitxml=test-results.xml
209+
PYTEST_EXIT_CODE=$?
210+
set -e
211+
212+
# Parse JUnit XML for test counts (cross-platform XML parsing)
213+
if [ -f "test-results.xml" ]; then
214+
# Extract counts from testsuite element
215+
PASSED=$(grep -oE 'tests="[0-9]+"' test-results.xml | grep -oE '[0-9]+' | head -1)
216+
FAILED=$(grep -oE 'failures="[0-9]+"' test-results.xml | grep -oE '[0-9]+' | head -1)
217+
SKIPPED=$(grep -oE 'skipped="[0-9]+"' test-results.xml | grep -oE '[0-9]+' | head -1)
222218
223219
# Default to 0 if not found
224220
PASSED=${PASSED:-0}
225-
SKIPPED=${SKIPPED:-0}
226221
FAILED=${FAILED:-0}
222+
SKIPPED=${SKIPPED:-0}
227223
228224
echo "passed=$PASSED" >> $GITHUB_OUTPUT
229225
echo "skipped=$SKIPPED" >> $GITHUB_OUTPUT
230226
echo "failed=$FAILED" >> $GITHUB_OUTPUT
231227
232-
# Exit with error if any failures
233-
if [ "$FAILED" != "0" ]; then
234-
exit 1
235-
fi
228+
echo "✅ Test results: $PASSED passed, $SKIPPED skipped, $FAILED failed"
236229
else
237-
echo "⚠️ Unexpected test output"
230+
echo "⚠️ test-results.xml not found"
238231
exit 1
239232
fi
240233
234+
# Exit with pytest's exit code
235+
exit $PYTEST_EXIT_CODE
236+
241237
- name: Generate test summary
242238
if: always()
243239
shell: bash

0 commit comments

Comments
 (0)