Le reporting de tests en CI couvre trois préoccupations. Stocker les artefacts (rapports HTML, traces, captures d'écran) pour que les échecs soient inspectables après l'exécution. Publier les résultats dans un format compris par le tableau de bord CI (JUnit XML). Remonter les échecs là où les développeurs regardent vraiment (commentaires de PR).
Le problème avec la sortie brute des tests
La sortie CI par défaut pour une exécution Playwright en échec ressemble à ceci :
✘ tests/login.spec.ts > shows error for wrong password (15234ms)
Error: Timed out 5000ms waiting for expect(locator).toBeVisible()
Call log:
- expect.toBeVisible with timeout 5000ms
- waiting for locator('[data-testid="error-message"]')Vous devez parcourir des centaines de lignes de sortie pour trouver les échecs. Dans une suite de 200 tests, c'est pénible.
Formats de rapport
JUnit XML
Le format universel : chaque système CI le comprend.
<?xml version="1.0" encoding="UTF-8"?>
<testsuites>
<testsuite name="Login Tests" tests="5" failures="1" time="12.5">
<testcase name="shows error for wrong password" time="15.2">
<failure message="Timed out waiting for error-message">
Error: Timed out 5000ms waiting for expect(locator).toBeVisible()
...
</failure>
</testcase>
<testcase name="successful login redirects to dashboard" time="3.2" />
</testsuite>
</testsuites>// playwright.config.ts
reporter: [
['junit', { outputFile: 'test-results/results.xml' }],
['list'], // Afficher aussi la sortie dans la console
],Rapport HTML
Le rapport HTML intégré de Playwright, visuel, avec captures d'écran et traces.
reporter: [
['html', { outputFolder: 'playwright-report', open: 'never' }],
],Générer et ouvrir en local :
npx playwright show-reportJSON
Format lisible par machine pour un traitement personnalisé :
reporter: [
['json', { outputFile: 'test-results/results.json' }],
],Utile pour construire des tableaux de bord personnalisés ou analyser les résultats par programme.
Reporters multiples
Vous voulez généralement plusieurs formats :
reporter: process.env.CI
? [
['junit', { outputFile: 'test-results/results.xml' }],
['html', { outputFolder: 'playwright-report', open: 'never' }],
['list'], // Sortie en temps réel dans les logs CI
]
: [
['html'], // En local : juste le rapport visuel
['list'],
],Intégration GitHub Actions
Configuration de base avec upload d'artefact
name: Playwright Tests
on: [push, pull_request]
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: 20
cache: npm
- run: npm ci
- run: npx playwright install --with-deps chromium
- name: Run tests
run: npx playwright test
env:
BASE_URL: ${{ secrets.STAGING_URL }}
# Toujours uploader le rapport, même quand les tests échouent
- name: Upload HTML report
uses: actions/upload-artifact@v4
if: always()
with:
name: playwright-report
path: playwright-report/
retention-days: 30
- name: Upload JUnit results
uses: actions/upload-artifact@v4
if: always()
with:
name: test-results
path: test-results/results.xmlLe if: always() est critique : sans lui, l'étape d'upload est ignorée quand les tests échouent.
Annotations de tests JUnit dans GitHub
GitHub Actions peut analyser le XML JUnit et annoter votre PR avec les échecs directement dans le diff :
- name: Report test results
uses: dorny/test-reporter@v1
if: always()
with:
name: Playwright Tests
path: test-results/results.xml
reporter: java-junit
fail-on-error: trueCela affiche un résumé dans l'interface PR de GitHub et annote les tests en échec dans le code.
Intégration GitLab CI
GitLab a un support natif JUnit :
test:
image: mcr.microsoft.com/playwright:v1.44.0-jammy
script:
- npm ci
- npx playwright test
artifacts:
when: always
reports:
junit: test-results/results.xml # Support JUnit natif
paths:
- playwright-report/ # Uploader aussi le rapport HTML
expire_in: 1 weekGitLab lit le XML JUnit et affiche un résumé de tests dans l'interface de pipeline, sans outils supplémentaires.
Notifications Slack
Envoyer des résumés d'échecs à Slack quand les tests CI échouent :
- name: Notify Slack on failure
if: failure()
uses: slackapi/slack-github-action@v1
with:
payload: |
{
"text": "❌ Playwright tests failed on ${{ github.ref_name }}",
"attachments": [{
"color": "danger",
"fields": [
{
"title": "Branch",
"value": "${{ github.ref_name }}",
"short": true
},
{
"title": "Run",
"value": "${{ github.run_id }}",
"short": true
},
{
"title": "Report",
"value": "${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }}"
}
]
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK }}Analyser les résultats par programme
Parfois vous avez besoin d'une logique personnalisée : notifier uniquement sur les nouveaux échecs, pas les ré-échecs.
// scripts/parse-results.js
const fs = require('fs');
const xml2js = require('xml2js');
async function parseResults() {
const xml = fs.readFileSync('test-results/results.xml', 'utf8');
const result = await xml2js.parseStringPromise(xml);
const testsuites = result.testsuites.testsuite;
const failures = [];
testsuites.forEach(suite => {
(suite.testcase || []).forEach(testcase => {
if (testcase.failure) {
failures.push({
name: testcase.$.name,
suite: suite.$.name,
message: testcase.failure[0].$.message,
time: testcase.$.time,
});
}
});
});
console.log(`Total failures: ${failures.length}`);
failures.forEach(f => {
console.log(`- [${f.suite}] ${f.name}`);
console.log(` ${f.message}`);
});
process.exit(failures.length > 0 ? 1 : 0);
}
parseResults();Commentaire résumé des tests sur les PRs
Commenter automatiquement un résumé de tests sur chaque PR :
- name: Test summary comment
uses: marocchino/sticky-pull-request-comment@v2
if: always()
with:
header: test-results
message: |
## Test Results
${{ steps.test-results.outputs.summary }}
[View full report](${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }})Rétention et historique
Les résultats bruts ne sont utiles que si vous les conservez assez longtemps.
GitHub Actions :- uses: actions/upload-artifact@v4
with:
retention-days: 30 # Conserver 30 joursCe qu'il faut mettre dans chaque rapport CI
Un rapport de tests utile répond à :
1. Combien de tests ont réussi / échoué / été ignorés ? Comptages résumés
2. Quels tests ont échoué ? Liste complète des échecs avec les noms des tests
3. Pourquoi ont-ils échoué ? Messages d'erreur et stack traces
4. À quoi ça ressemble ? Captures d'écran pour les tests UI
5. Combien de temps ça a pris ? Temps d'exécution par test
6. Est-ce un nouvel échec ? Comparaison avec l'exécution précédente
Le rapport HTML de Playwright couvre les points 1 à 5. Les outils de tendance (Allure, TestOps) ajoutent le 6.
Résumé
| Format | Idéal pour |
|---|---|
| JUnit XML | Intégration avec le système CI, annotations de PR |
| HTML | Lecture humaine, captures d'écran, traces |
| JSON | Traitement personnalisé, tableaux de bord |
| List | Sortie console en temps réel |
Configuration minimale pour la CI :1. Générer le XML JUnit (la CI peut le lire)
2. Uploader le rapport HTML comme artefact
3. Utiliser if: always() sur les étapes d'upload
- Rapport Allure avec tendances
- Notification Slack en cas d'échec
- Commentaire de PR avec résumé
- Annotation de test dans la vue diff