Polytech Tours · Qualité, Test & Sécurité · 4A / 5A
L'application existe et fonctionne. Votre mission n'est pas de la développer, c'est de challenger ses spécifications, l'éprouver par le test, et construire la chaîne CI/CD qui garantit sa qualité à chaque commit.
1 · Le contexte
L'association Corpo Padel organise des tournois de padel inter-entreprises. Elle s'est fait développer une application web (un frontend Vue 3, un backend FastAPI) par un prestataire pressé. L'application marche… en apparence.
Mais il n'existe aucun test, aucune chaîne d'intégration, et plusieurs anomalies ont déjà été remontées par les utilisateurs sans qu'on parvienne à les caractériser. Les spécifications, elles-mêmes, méritent un regard critique.
Votre équipe reprend le projet en tant qu'ingénieurs qualité. Vous n'écrirez aucune nouvelle fonctionnalité. Vous allez revoir les specs, éprouver l'application, prouver ses défauts, et la doter d'une chaîne CI/CD automatisée, exactement la démarche vue en cours.
2 · Objectifs pédagogiques
push et pull request.3 · Déroulé du TP
Cliquez sur une phase pour la déplier. Les sept phases sont attendues de tous les groupes.
Tester commence avant d'exécuter la moindre ligne. Comprendre le besoin, et challenger les spécifications : sont-elles complètes, cohérentes, sans ambiguïté, et surtout testables ?
Disposer d'un dépôt de groupe qui vous appartient (indispensable pour la CI) et d'une application qui tourne.
README multi-OS./docs).Éprouver l'application à la main, de façon structurée, et caractériser chaque défaut. L'application contient des anomalies volontaires : à vous de les débusquer.
Transposer vos cas de recette manuels les plus importants en tests automatisés qui rejouent les parcours dans un vrai navigateur.
Tester directement l'API FastAPI, indépendamment du frontend, et mesurer la proportion de code réellement couverte.
pytest --cov et viser ≥ 70 % du code applicatif.Construire un workflow qui exécute automatiquement vos tests à chaque modification, matérialisant les portes de qualité du cours. La procédure détaillée pas-à-pas est en annexe B.
push et pull_request.main protégée, PR validée par la CI obligatoire avant merge.main..github/workflows/ci.yml vert + badge4 · Un sujet, deux ambitions
Le sujet est identique pour tous les groupes. Il se joue sur deux axes complémentaires, l'un et l'autre attendus dans votre rendu.
Challenger les spécifications, éprouver l'application à la main, formaliser chaque défaut en fiche d'anomalie, puis transposer vos cas de recette en tests automatisés. C'est ce qui établit si l'application fait, ou non, ce que le cahier des charges annonce.
Construire la pipeline qui rejoue tout automatiquement à chaque commit : lint, tests back-end, tests E2E, quality gate sur la couverture, branches protégées et déploiement continu. C'est ce qui garantit que la qualité tient dans le temps.
5 · Évaluation
| Critère | Points | Attendu |
|---|---|---|
| Revue de specs & matrice de traçabilité | 2 | Ambiguïtés relevées, traçabilité exigence → test |
| Plan de test & cahier de recette | 2 | Structure, cas limites & cas d'erreur |
| Fiches d'anomalies | 2 | Complétude, reproductibilité, sévérité juste |
| Tests E2E (Cypress / Selenium) | 3 | Parcours visiteur / joueur / admin rejouables |
| Tests back-end pytest + couverture | 3 | Couverture ≥ 70 %, scénarios métier |
| Pipeline CI/CD fonctionnelle | 1.5 | Lint + tests sur push/PR, badge |
| Rapport | 0.5 | Clarté, lien avec le cours |
| Quality gate couverture | 1.5 | Pipeline rouge sous le seuil défini |
| Tests de sécurité OWASP | 2 | Contrôle d'accès, XSS, brute force, intégrés en CI |
| Déploiement continu | 1.5 | Déploiement auto sur merge vers main |
| Branches protégées & métriques DORA | 1 | PR obligatoire + lecture DORA argumentée |
6 · Livrables
Un dépôt Git par groupe (votre fork), dont le lien est communiqué à l'enseignant avant la date limite. Organisation attendue :
Annexe A
Chaque défaut donne lieu à une fiche au format suivant. Une fiche décrit un seul problème, assez précisément pour qu'un développeur le reproduise sans vous.
| Champ | Contenu |
|---|---|
| ID | ANO-001, ANO-002… |
| Titre | Court et descriptif |
| Type | Fonctionnel · Sécurité · IHM |
| Sévérité | Bloquant · Critique · Majeur · Mineur · Cosmétique |
| Module / endpoint | La page ou la route concernée |
| Environnement | Navigateur, OS, version testée |
| Pré-requis | État initial, compte utilisé (rôle) |
| Étapes de reproduction | Numérotées, déterministes |
| Résultat attendu | Comportement correct selon le cahier des charges |
| Résultat obtenu | Comportement réellement observé |
| Preuve | Capture, log, ou réponse API (corps + code HTTP) |
| Correction suggérée | Optionnel, hypothèse sur l'origine |
Annexe B
Construisez votre pipeline progressivement. Chaque étape est testable avant de passer à la suivante.
À la racine de votre dépôt, créez le fichier .github/workflows/ci.yml. GitHub détecte automatiquement tout fichier YAML dans ce dossier et le traite comme une pipeline.
Premier job : lint + tests pytest sur l'API. Poussez ce fichier, puis vérifiez l'onglet Actions de votre dépôt : la pipeline doit se déclencher et passer au vert.
name: CI on: push: pull_request: jobs: backend: runs-on: ubuntu-latest defaults: run: working-directory: backend steps: - uses: actions/checkout@v4 - uses: actions/setup-python@v5 with: python-version: '3.11' - name: Installer les dépendances run: | python -m pip install --upgrade pip pip install -r requirements.txt pip install flake8 pytest pytest-cov - name: Lint (flake8) run: flake8 app --max-line-length=100 - name: Tests + couverture run: pytest --cov=app --cov-report=term
Second job : il faut que le backend ET le frontend tournent pendant les tests Cypress. On installe Python (pour servir l'API), on lance l'API en arrière-plan, puis l'action officielle Cypress démarre le frontend et attend que les deux soient prêts.
e2e:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
# --- Backend : servir l'API pendant les tests ---
- uses: actions/setup-python@v5
with:
python-version: '3.11'
- name: Installer + démarrer l'API
working-directory: backend
run: |
pip install -r requirements.txt
python seed.py
uvicorn app.main:app --port 8000 &
# le '&' lance l'API en arrière-plan
# --- Frontend + Cypress ---
- uses: actions/setup-node@v4
with:
node-version: '20'
- name: Configurer l'URL de l'API
working-directory: frontend
run: echo "VITE_API_BASE_URL=http://localhost:8000/api/v1" > .env
- name: Lint (ESLint)
working-directory: frontend
run: npm ci && npm run lint
- name: Tests E2E Cypress
uses: cypress-io/github-action@v6
with:
working-directory: frontend
start: npm run dev
wait-on: 'http://localhost:5173, http://localhost:8000/docs'
wait-on-timeout: 120
En haut de votre README.md, ajoutez le badge (remplacez OWNER et REPO par les vôtres) :

Faites échouer la pipeline si la couverture descend sous 70 %. Modifiez l'étape de test back-end :
- name: Tests + quality gate
run: pytest --cov=app --cov-fail-under=70
mainDans Settings → Branches → Add branch ruleset : exigez une pull request avant merge, et cochez « Require status checks to pass » en sélectionnant vos jobs backend et e2e. Plus aucun code ne rejoint main sans passer la CI.
C'est exactement le passage « changement normal → changement standard » du cours : la pipeline devient le contrôle.
Ajoutez un job qui ne s'exécute que sur main et qui publie le frontend après le passage des tests :
deploy:
needs: [backend, e2e]
if: github.ref == 'refs/heads/main'
runs-on: ubuntu-latest
permissions:
pages: write
id-token: write
steps:
- uses: actions/checkout@v4
- uses: actions/setup-node@v4
with:
node-version: '20'
- name: Build du frontend
working-directory: frontend
run: npm ci && npm run build
- uses: actions/upload-pages-artifact@v3
with:
path: frontend/dist
- uses: actions/deploy-pages@v4
Annexe C
# Back-end - tests & couverture (depuis backend/, venv activé) pytest # lancer les tests pytest --cov=app --cov-report=term # couverture console pytest --cov=app --cov-report=html # rapport HTML pytest --cov=app --cov-fail-under=70 # avec quality gate # Front-end - Cypress (depuis frontend/, back + front lancés) npx cypress open # mode interactif npx cypress run # mode headless (CI) # Lint flake8 app/ # Python npm run lint # Vue # Git - bonne hygiène git checkout -b feat/tests-auth # une branche par lot de travail git commit -m "test(auth): cas login KO" # messages clairs