43
lien Charpentier – Directeur R&D rille Grandval – Directeur Général Tests Unitaires « Je veux mes 80% de couverture de code » 24.06.201 PHP Tour Lyon 201

PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Embed Size (px)

DESCRIPTION

De nos jours de plus en plus d'entreprises ne jurent que par les tests unitaires. Faire du test, faire du test, faire du test ! “Une application n'est pérenne que si elle est testée et elle est testée si plus de 80% du code est couvert.” Cela devient même un élément décisif du recruteur en entretien : - Votre collaborateur a l'air vraiment bien mais... Il a déjà fait des tests unitaires ? Il a plus de deux ans d'expérience là dessus ? - Juste sur deux projets, par contre il possède la bonne philosophie. - Ah oui mais non il faut qu'il en ait fait 2 ans, c'est un minimum. On cherche des experts nous ! Problématique : "Je veux minimum 80% de couverture de code !!!" Qui n'a pas entendu cette phrase dans la bouche d'un chef de projet ou d'un lead dev trop consciencieux sans doute. Dans certains projets un test unitaire est bon si il couvre au moins 80% de la fonctionnalité à tester, c'est tout ce qui est demandé et c'est cela qu'il faut avoir. Il est avant tout essentiel de s'interroger sur la notion de couverture de code dans un test unitaire : La couverture de code est-elle un but ? un facteur qualité ? une représentation visuelle d'un test ? Ou est-ce cet horrible fantôme qui vient hanter une application ? Pour faire simple : un test qui couvre 100% du code à tester est-il forcement fiable ? Conférence PHPTour Lyon 2014 - Tests unitaires - Je veux mes 80% de couverture de code !!!! http://afup.org/pages/phptourlyon2014/sessions.php#1094

Citation preview

Page 1: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Julien Charpentier – Directeur R&DCyrille Grandval – Directeur Général

Tests Unitaires

« Je veux mes 80% de couverture de code »

24.06.2014PHP Tour Lyon 2014

Page 2: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Qui sommes nous?

Cyrille GrandvalDirecteur général Darkmira

Consultant sécuritéAuteur

[email protected]@CyrilleGrandval

Julien CharpentierDirecteur R&DLead Dev PHP

Auteur

[email protected]@jcharpentier_

Page 3: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Darkmira

Développement PHP sécurisé

Industrialisation

Sécurité Bonnes pratiques

@DarkmiraBrasilwww.darkmira.com.br

@Darkmira1www.darkmira.fr

Page 4: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Historique des tests unitaires

1994 (K.Beck) : SUnit pour SmallTalk

1997 (K.Beck & E.Gamma) : JUnit pour Java

1999 (K.Beck) : XP => TDD

Multiples frameworks créés (xUnit)

Notamment pour PHP : PHPUnit (S.Bergmann)SimpleTest (en fin de vie)Atoum (F.Hardy)

Page 5: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Tests unitaires aujourd’hui…

Préconisés par les techniques de développement logiciel dans lesquels ils sont mis à l’honneur• TDD (Tests Driven Development)• BDD (Behaviour Driven Development)• PDD (Pragmatism Driven Development)

• merci à Gabriel Pillet :)

Dans les esprits :• Pratiqués par les développeurs et attendus par les responsables de projets

Dans la réalité :• Pas le temps• ROI difficilement quantifiable• Armada de tests unitaires obsolètes, en échec mais ignorés• Justification de non écriture systématique• Fausses pistes de recherche de résolution de bugs

Page 6: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Et de plus en plus…

C2DT (Code Coverage Driven Tests)

Je veux au minimum 80% de

couverture de code!!!!!!

Page 7: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code
Page 8: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Couverture de code : indicateur quantitatif ou qualitatif ?

Extrait de wikipedia“La couverture de code (en anglais code coverage) est une mesure utilisée en génie logiciel pour décrire le taux de code source testé d'un programme. Ceci permet de mesurer la qualité des tests effectués.Car plus un programme est bien testé, moins il est soumis aux bugs.”

Différentes couvertures

Les outils pour PHP nous donne le taux de la couverture des instructions => QUANTITATIF

• Points de tests• Chemins d’exécution

Quantitative• Fonctions• Instructions

Qualitative

Page 9: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

100% de couverture de code = application testée ?

Page 10: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Une invitation aux mauvaises pratiquesQue font la plupart des développeurs?

Couverture de code : un trompe l’œil ?

Je test un comportement

Je passe à un test d’un autre

comportement

NON

OUIJ’écris un test

Je vérifie la couverture

>80%

Page 11: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Couverture de code : un trompe l’œil ?

class Bar { public function drink($a, $b) { $x = '';

if (1 == $b) { $x .= 'B'; } else { $x .= 'E'; }

if (1 == $b) { $x .= 'R'; } else { $x .= 'E'; }

return $x; }}

class BarTest extends PHPUnit_Framework_TestCase{ protected function setUp() { parent::setUp (); $this->Bar = new Bar(); }

public function testBar() { $sDrink = $this->Bar->drink(1, 2); $this->assertEquals('BE', $sDrink);

$sDrink = $this->Bar->drink(2, 1); $this->assertEquals('ER', $sDrink); }}

Page 12: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Représentation graphique

Couverture de code : un trompe l’œil ?

Page 13: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Instructions : 100%Chemins d’exécution : 50%

Représentation graphique

Couverture de code : un trompe l’œil ?

Page 14: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Couverture de code : un trompe l’œil ?

100% de couverture de code = application testée

N’assure pas que :• Des assertions sont présentes• Qu’elles testent les bons comportements• Que les tests soient vraiment unitaires• Que le test soit lisible et bien écrit• Que les cas d’entrée soient clairement identifiés

Que le test soit un test unitaire

Page 15: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Couverture de code : conséquences

Une plaie pour les développeurs• Ils ne comprennent pas l’utilité• Ils ne comprennent pas comment écrire les tests• Ils ont l’impression de perdre leur temps

C’est inutile et contre-productif• Laisser-aller• Incompréhension• Perte de temps• Builds trop longs

Une bombe à retardement• Coûts de développement trop élevés• Coûts de maintenance trop élevés• Perte de confiance• TU obsolètes et ignorés• Application vulnérable

Page 16: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Couverture de code : conséquences

Page 17: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

C’est un risque bien réel

Page 18: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

C2DT : Tue la politique de tests unitairesOutils pas assez matures pour PHPIndicateur uniquement quantitatifN’atteste pas de la qualité des tests unitaires => La vérité est ailleurs

Page 19: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

80% !???

Page 20: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

LE CODE DE TEST N’EST PAS QUE DU CODE

DE TEST !!!

Page 21: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

La qualité à l’état naturel

• Philosophie• Bonnes pratiqueso Conventionso Lisibilitéo Commentaires

• Bons outils

Page 22: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

La qualité à l’état naturel : Intro

Qu’est ce qu’un test unitaire ?• Un test unitaire consiste à isoler un comportement de tout facteur extérieur et de vérifier qu’il est conforme à ce que vous attendez.

Pourquoi teste-t-on ?• Vérifier

Quels sont les avantages ?

• Documenter• Automatiser

Sérénité

Ne plus avoir peur de modifier le code

Comprendre un code que l’on n’a pas écrit

Supprimer du code sans perdre de fonctionnalité

Facilité de la maintenance

S’assurer de la non régression

Page 23: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

La qualité à l’état naturel : Philosophie

Coder en pensant test…• Coder l’application pour qu’elle soit naturellement et unitairement testable• Veiller à garder un couplage faible• Utiliser l’injection de dépendance• Veiller à limiter la complexité cyclomatique• Faire des revues de codes ou du pair programming• Ne pas propager un code qui peut-être refactorisé

…et tester en pensant qualité de la couverture• Rechercher le taux de couverture des chemins d’exécution le plus haut possible• Tester en boîte blanche

o Identifier et tester toutes les entrées possibles…o …et vérifier les sorties attendues correspondantes

• Ne pas se limiter aux cas simpleso Tester les cas nominaux…o …mais aussi les cas en erreur et les cas limites

Page 24: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

La qualité à l’état naturel : Bonnes pratiques

10 règles à respecter

• Un test unitaire doit-être UNITAIRE !• Utilisez les mocks et/ou stubs (100% des appels externes)• Un test est avant tout du code : il doit simple, normé, commenté, facile à lire et à

comprendre • Un test doit être rapide à exécuter• Les tests doivent être écrits le plus tôt possible• Un test = une assertion (ou presque)• Testez en priorité les parties critiques de l’application• Écrivez le code de l’application pour qu’il soit testable• Refactorisez !• Le nom d’un test est capital, normalisez le !

ex: testNomMethode_EtatDepart_ComportementAttendu donnera testOpenFile_FileNoExists_ThrowException()

Page 25: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

La qualité à l’état naturel : Bonnes pratiques

10 règles à respecter

• Un test unitaire doit-être UNITAIRE !• Utilisez les mocks et/ou stubs (100% des appels externes)• Un test est avant tout du code : il doit simple, normé, commenté, facile à lire et à

comprendre • Un test doit être rapide à exécuter• Les tests doivent être écrits le plus tôt possible• Un test = une assertion (ou presque)• Testez en priorité les parties critiques de l’application• Écrivez le code de l’application pour qu’il soit testable• Refactorisez !• Le nom d’un test est capital, normalisez le !

Page 26: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

La qualité à l’état naturel : Bonnes pratiques

10 règles à respecter

• Un test unitaire doit-être UNITAIRE !• Utilisez les mocks et/ou stubs (100% des appels externes)• Un test est avant tout du code : il doit simple, normé, commenté, facile à lire et à

comprendre • Un test doit être rapide à exécuter• Les tests doivent être écrits le plus tôt possible• Un test = une assertion (ou presque)• Testez en priorité les parties critiques de l’application• Écrivez le code de l’application pour qu’il soit testable• Refactorisez !• Le nom d’un test est capital, normalisez le !

Page 27: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

La qualité à l’état naturel : Bonnes pratiques

10 règles à respecter

• Un test unitaire doit-être UNITAIRE !• Utilisez les mocks et/ou stubs (100% des appels externes)• Un test est avant tout du code : il doit simple, normé, commenté, facile à lire et à

comprendre • Un test doit être rapide à exécuter• Les tests doivent être écrits le plus tôt possible• Un test = une assertion (ou presque)• Testez en priorité les parties critiques de l’application• Écrivez le code de l’application pour qu’il soit testable• Refactorisez !• Le nom d’un test est capital, normalisez le !

Page 28: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

La qualité à l’état naturel : Bonnes pratiques

10 règles à respecter

• Un test unitaire doit-être UNITAIRE !• Utilisez les mocks et/ou stubs (100% des appels externes)• Un test est avant tout du code : il doit simple, normé, commenté, facile à lire et à

comprendre • Un test doit être rapide à exécuter• Les tests doivent être écrits le plus tôt possible• Un test = une assertion (ou presque)• Testez en priorité les parties critiques de l’application• Écrivez le code de l’application pour qu’il soit testable et refactorisez !• Utiliser les design pattern (ex : AAA)• Le nom d’un test est capital, normalisez le !

test[NomMethode][EtatDeDepart][ComportementAttendu]

Page 29: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code
Page 30: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code
Page 31: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

10 pièges à éviter

• Avoir pour but la couverture de code :)• Écrire un test illisible• Écrire un test non isolé

o dépendant de facteurs extérieurs (temps)o dépendant de l'environnement (système de fichiers, base de données,

webservices, ...)o dépendant d’un autre test

• Écrire les tests quand on a le temps• Décorréler le test et le code testé

o Ecrire un test sans comprendre le comportement testéo Écrire un test sans refactoriser un code qui doit l’être

• Confondre test unitaire et test d’intégration• Ne pas exécuter les TU à chaque commit / push sur le dépot• Écrire un test par comportement testé• Ecrire un test gérant plusieurs états• Faire trop de tests unitaires !

La qualité à l’état naturel : Mauvaises pratiques

Page 32: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

10 pièges à éviter

• Avoir pour but la couverture de code :)• Écrire un test illisible• Écrire un test non isolé

o dépendant de facteurs extérieurs (temps)o dépendant de l'environnement (système de fichiers, base de données,

webservices, ...)o dépendant d’un autre test

• Écrire les tests quand on a le temps• Décorréler le test et le code testé

o Ecrire un test sans comprendre le comportement testéo Écrire un test sans refactoriser un code qui doit l’être

• Confondre test unitaire et test d’intégration• Ne pas exécuter les TU à chaque commit / push sur le dépot• Écrire un test par comportement testé• Ecrire un test gérant plusieurs états• Faire trop de tests unitaires !

La qualité à l’état naturel : Mauvaises pratiques

Page 33: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

10 pièges à éviter

• Avoir pour but la couverture de code :)• Écrire un test illisible• Écrire un test non isolé

o dépendant de facteurs extérieurs (temps)o dépendant de l'environnement (système de fichiers, base de données,

webservices, ...)o dépendant d’un autre test

• Écrire les tests quand on a le temps• Décorréler le test et le code testé

o Ecrire un test sans comprendre le comportement testéo Écrire un test sans refactoriser un code qui doit l’être

• Confondre test unitaire et test d’intégration• Ne pas exécuter les TU à chaque commit / push sur le dépot• Écrire un test par comportement testé• Ecrire un test gérant plusieurs états• Faire trop de tests unitaires !

La qualité à l’état naturel : Mauvaises pratiques

Page 34: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

10 pièges à éviter

• Avoir pour but la couverture de code :)• Écrire un test illisible• Écrire un test non isolé

o dépendant de facteurs extérieurs (temps)o dépendant de l'environnement (système de fichiers, base de données,

webservices, ...)o dépendant d’un autre test

• Écrire les tests quand on a le temps• Décorréler le test et le code testé

o Ecrire un test sans comprendre le comportement testéo Écrire un test sans refactoriser un code qui doit l’être

• Confondre test unitaire et test d’intégration• Ne pas exécuter les TU à chaque commit / push sur le dépot• Écrire un test par comportement testé• Ecrire un test gérant plusieurs états• Faire trop de tests unitaires !

La qualité à l’état naturel : Mauvaises pratiques

Page 35: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Tester la qualité : le Mutation Testing

Tester le test lui-même

Page 36: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Un peu d’histoire

• 1971 (Richard Lipton) – Concept

• 1980 (Timothy Budd) - Premier outil

• Constat : Les tests vérifient que l’application est l'implémentation correcte des besoins. Sont-ils suffisamment qualifiés ? Repèrent-t-ils un dysfonctionnement ?

• Objectif : Créer des mutations simples du code source d’une application et soumettre ces mutations à la suite de tests unitaires.

• Score qualitatif = nombre de mutants tués / nombre de mutants créés

Tester la qualité : le Mutation Testing

Page 37: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Fonctionnement

• Le mutation-testing utilise un lot de mutations simples qu’il applique une à une sur le code source original de l’application.

• Il crée ainsi des mutations du code original qui en modifie son comportement.

• Ce comportement étant différent, certains tests devraient logiquement le repérer et ne plus être acceptés

• Exemples de mutations :o modification de conditions (== par !=, == par =, && par ||, > par <, etc.)o modification structurelles (suppression de bloc else, d’un case de switch, etc.)o modification de valeurs (true par false, …)

Tester la qualité : le Mutation Testing

Page 38: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Tester la qualité : le Mutation Testing

Exemple 1

if ($a && $b) { $c = 1;} else { $c = 0;}

L’opérateur de condition && va être remplacé

par ||

if ($a || $b) { $c = 1;} else { $c = 0;}

Si $a = true et $b = false, le comportement est différent du code original, $c sera égal

à 1 au lieu d’être à 0.Un test unitaire va-t-il

repérer cela ?

Page 39: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Tester la qualité : le Mutation Testing

Exemple 2

if ($a && $b) { $c = 1;} else { $c = 0;}

Le bloc else va être supprimé

if ($a && $b) { $c = 1;}

Si $a et/ou $b sont égaux à false, le comportement est

différent du code original, $c ne sera pas défini au lieu d’être

égal à 0.Un test unitaire va-t-il repérer

cela ?

Page 40: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Tester la qualité : le Mutation Testing

Ce qui impose donc au test, pour tuer le mutant :• de couvrir l’instruction mutante• de prendre en compte l’entrée qui donne vie au mutant• d’être capable de vérifier que la sortie mutante n’est pas attendue

et impose au code, de propager la ou les valeurs mutantes en sortie.

Cela vérifie donc bien :• la couverture des instructions• la couverture des chemins d’exécution• la couverture des points de tests• la couverture des E/S

Page 41: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Tester la qualité : le Mutation Testing

Outils pour PHP• 2013 (Jean-François Lépine) MutaTesting

o PHP 5.3+o Ne nécessite pas d’extensiono Indépendant du framework de testso Ne nécessite pas de code en pluso Intégrable facilement dans un outil d’intégration continue (type Jenkins)o Ne crée pas les mutants physiquement

(Source : https://github.com/Halleck45/MutaTesting/)

Page 42: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code
Page 43: PHPTour Lyon 2014 - Conférence - Tests unitaires Je veux mes 80% de couverture de code

Des questions???

Merci !