fin de séance
This commit is contained in:
commit
14851fbf4f
1
.gitignore
vendored
Normal file
1
.gitignore
vendored
Normal file
|
@ -0,0 +1 @@
|
|||
*.class
|
11
.vscode/settings.json
vendored
Normal file
11
.vscode/settings.json
vendored
Normal file
|
@ -0,0 +1,11 @@
|
|||
{
|
||||
"files.exclude": {
|
||||
"**/.git": true,
|
||||
"**/.svn": true,
|
||||
"**/.hg": true,
|
||||
"**/CVS": true,
|
||||
"**/.DS_Store": true,
|
||||
"**/Thumbs.db": true,
|
||||
"**/*.class": true
|
||||
}
|
||||
}
|
10
Apres.java
Normal file
10
Apres.java
Normal file
|
@ -0,0 +1,10 @@
|
|||
import java.lang.annotation.ElementType;
|
||||
import java.lang.annotation.Retention;
|
||||
import java.lang.annotation.RetentionPolicy;
|
||||
import java.lang.annotation.Target;
|
||||
|
||||
@Target(ElementType.METHOD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface Apres {
|
||||
|
||||
}
|
19
Assert.java
Normal file
19
Assert.java
Normal file
|
@ -0,0 +1,19 @@
|
|||
/** La classe Assert définit des méthodes de vérification. Pour l'instant, la
|
||||
* seule méthode de vérification est assertTrue mais d'autres pourraient être
|
||||
* définies (voir JUnit).
|
||||
*
|
||||
* @author Xavier Crégut
|
||||
* @version $Revision: 1.1 $
|
||||
*/
|
||||
abstract public class Assert {
|
||||
|
||||
/** Vérifier que la condition est vraie.
|
||||
* @param condition la condition à vérifier
|
||||
*/
|
||||
static public void assertTrue(boolean condition) {
|
||||
if (! condition) {
|
||||
throw new Echec();
|
||||
}
|
||||
}
|
||||
|
||||
}
|
7
Avant.java
Normal file
7
Avant.java
Normal file
|
@ -0,0 +1,7 @@
|
|||
import java.lang.annotation.*;
|
||||
|
||||
@Target(ElementType.METHOD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface Avant {
|
||||
|
||||
}
|
35
CasLimitesTest.java
Normal file
35
CasLimitesTest.java
Normal file
|
@ -0,0 +1,35 @@
|
|||
/** Tester quelques cas limites.
|
||||
* @author Xavier Crégut
|
||||
* @version $Revision$
|
||||
*/
|
||||
public class CasLimitesTest {
|
||||
|
||||
public void testOK() {
|
||||
// OK.
|
||||
}
|
||||
|
||||
private void testMethodePrivee() {
|
||||
throw new RuntimeException("Une méthode privée n'est pas un test !");
|
||||
}
|
||||
|
||||
protected void testMethodeProtegee() {
|
||||
throw new RuntimeException("Une méthode protected n'est pas un test !");
|
||||
}
|
||||
|
||||
void testMethodePaquetage() {
|
||||
throw new RuntimeException("Une méthode de droit d'accès paquetage n'est pas un test !");
|
||||
}
|
||||
|
||||
public static void testMethodeDeClasse() {
|
||||
throw new RuntimeException("Une méthode de classe n'est pas un test !");
|
||||
}
|
||||
|
||||
public void testAvecParametre(int a) {
|
||||
throw new RuntimeException("Une méthode avec des paramètres n'est pas un test !");
|
||||
}
|
||||
|
||||
public void testAvecParametre2(int a) {
|
||||
throw new RuntimeException("Une méthode avec des paramètres n'est pas un test !");
|
||||
}
|
||||
|
||||
}
|
13
DeviseInvalideException.java
Normal file
13
DeviseInvalideException.java
Normal file
|
@ -0,0 +1,13 @@
|
|||
/** L'exception DeviseInvalideException indique des devises incompatibles sur
|
||||
* des opérations entre monnaies.
|
||||
*
|
||||
* @author Xavier Crégut
|
||||
* @version $Revision: 1.1 $
|
||||
*/
|
||||
public class DeviseInvalideException extends Exception {
|
||||
|
||||
public DeviseInvalideException(String message) {
|
||||
super(message);
|
||||
}
|
||||
|
||||
}
|
12
Echec.java
Normal file
12
Echec.java
Normal file
|
@ -0,0 +1,12 @@
|
|||
/** L'exception Echec permet de signaler l'erreur fonctionnelle d'un test.
|
||||
* @author Xavier Crégut
|
||||
* @version $Revision: 1.1 $
|
||||
*/
|
||||
public class Echec extends Error {
|
||||
public Echec() {
|
||||
super("condition non vérifiée");
|
||||
}
|
||||
public Echec(String message) {
|
||||
super(message);
|
||||
}
|
||||
}
|
17
ErreurTest.java
Normal file
17
ErreurTest.java
Normal file
|
@ -0,0 +1,17 @@
|
|||
/** ErreurTest est un programme de test qui définit trois méthodes de test
|
||||
* dont une provoque une erreur.
|
||||
*/
|
||||
public class ErreurTest {
|
||||
|
||||
public void tester1() {
|
||||
}
|
||||
|
||||
public void tester2() {
|
||||
Assert.assertTrue(false);
|
||||
}
|
||||
|
||||
public void tester3() {
|
||||
Assert.assertTrue(true);
|
||||
}
|
||||
|
||||
}
|
3
FausseException.java
Normal file
3
FausseException.java
Normal file
|
@ -0,0 +1,3 @@
|
|||
public class FausseException extends Exception {
|
||||
|
||||
}
|
147
LanceurIndependant.java
Normal file
147
LanceurIndependant.java
Normal file
|
@ -0,0 +1,147 @@
|
|||
import java.lang.reflect.*;
|
||||
import java.util.*;
|
||||
import java.lang.annotation.*;
|
||||
|
||||
/**
|
||||
* L'objectif est de faire un lanceur simple sans utiliser toutes les clases de
|
||||
* notre architecture JUnit. Il permet juste de valider la compréhension de
|
||||
* l'introspection en Java.
|
||||
*/
|
||||
public class LanceurIndependant {
|
||||
private int nbTestsLances;
|
||||
private int nbErreurs;
|
||||
private int nbEchecs;
|
||||
private List<Throwable> erreurs = new ArrayList<>();
|
||||
|
||||
public LanceurIndependant(String... nomsClasses) {
|
||||
System.out.println();
|
||||
|
||||
// Lancer les tests pour chaque classe
|
||||
for (String nom : nomsClasses) {
|
||||
try {
|
||||
System.out.println(nom + " : ");
|
||||
this.testerUneClasse(nom);
|
||||
System.out.println();
|
||||
} catch (ClassNotFoundException e) {
|
||||
System.out.println("Classe inconnue !");
|
||||
} catch (Exception e) {
|
||||
System.out.println("Problème : " + e);
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
// Afficher les erreurs
|
||||
for (Throwable e : erreurs) {
|
||||
System.out.println();
|
||||
e.printStackTrace();
|
||||
}
|
||||
|
||||
// Afficher un bilan
|
||||
System.out.printf("%d tests lancés dont %d échecs et %d erreurs.", nbTestsLances, nbEchecs, nbErreurs);
|
||||
}
|
||||
|
||||
public int getNbTests() {
|
||||
return this.nbTestsLances;
|
||||
}
|
||||
|
||||
public int getNbErreurs() {
|
||||
return this.nbErreurs;
|
||||
}
|
||||
|
||||
public int getNbEchecs() {
|
||||
return this.nbEchecs;
|
||||
}
|
||||
|
||||
private void testerUneClasse(String nomClasse)
|
||||
throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException,
|
||||
IllegalArgumentException, InvocationTargetException, SecurityException {
|
||||
// Récupérer la classe
|
||||
Class<?> classe = Class.forName(nomClasse);
|
||||
|
||||
// Récupérer les méthodes "preparer" et "nettoyer"
|
||||
Method preparer = null;
|
||||
Method nettoyer = null;
|
||||
|
||||
for (Method method : classe.getMethods()) {
|
||||
if (method.isAnnotationPresent(Avant.class)) {
|
||||
preparer = method;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
for (Method method : classe.getMethods()) {
|
||||
if (method.isAnnotationPresent(Apres.class)) {
|
||||
nettoyer = method;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// Instancier l'objet qui sera le récepteur des tests
|
||||
// Object objet = classe.newInstance();
|
||||
Object objet = classe.getDeclaredConstructor().newInstance();
|
||||
|
||||
// Exécuter les méthods de test
|
||||
Method[] methods = classe.getMethods();
|
||||
for (Method method : methods) {
|
||||
if (method.isAnnotationPresent(UnTest.class)) {
|
||||
if (method.getAnnotation(UnTest.class).enabled()) {
|
||||
|
||||
this.nbTestsLances++;
|
||||
|
||||
if (preparer != null) {
|
||||
preparer.invoke(objet);
|
||||
}
|
||||
|
||||
Class<? extends Throwable> exep = method.getAnnotation(UnTest.class).expected();
|
||||
|
||||
try {
|
||||
if (exep != FausseException.class) {
|
||||
System.out.println("exep != FausseException.class");
|
||||
try {
|
||||
method.invoke(objet);
|
||||
System.out.println(method.getName() + " : echec");
|
||||
this.nbEchecs++;
|
||||
} catch (InvocationTargetException e) {
|
||||
Class<? extends Throwable> exep2 = method.getAnnotation(UnTest.class).expected();
|
||||
if (e.getCause().getClass().isAssignableFrom(exep)) {
|
||||
System.out.println(method.getName() + " : success");
|
||||
} else {
|
||||
System.out.println(method.getName() + " : erreur");
|
||||
this.erreurs.add(e);
|
||||
this.nbErreurs++;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
try {
|
||||
method.invoke(objet);
|
||||
System.out.println(method.getName() + " : success");
|
||||
} catch (InvocationTargetException e) {
|
||||
if (e.getCause() instanceof Echec) {
|
||||
System.out.println(method.getName() + " : echec");
|
||||
this.erreurs.add(e);
|
||||
this.nbEchecs++;
|
||||
} else {
|
||||
System.out.println(method.getName() + " : erreur");
|
||||
this.erreurs.add(e);
|
||||
this.nbErreurs++;
|
||||
}
|
||||
}
|
||||
}
|
||||
} catch (java.lang.IllegalArgumentException e) {
|
||||
System.out.println(method.getName() + " : erreur, pas de test avec arguments");
|
||||
this.nbErreurs++;
|
||||
System.out.println("d");
|
||||
}
|
||||
|
||||
if (nettoyer != null) {
|
||||
nettoyer.invoke(objet);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static void main(String... args) {
|
||||
new LanceurIndependant(args);
|
||||
}
|
||||
}
|
59
Monnaie.java
Normal file
59
Monnaie.java
Normal file
|
@ -0,0 +1,59 @@
|
|||
/** La classe Monnaie est caractérisée par une valeur et une devise. Deux
|
||||
* monnaies peuvent être ajoutées ou retranchées.
|
||||
*
|
||||
* @author Xavier Crégut
|
||||
* @version $Revision: 1.1 $
|
||||
*/
|
||||
public class Monnaie {
|
||||
private int valeur;
|
||||
private String devise;
|
||||
|
||||
/** Initialiser une monnaie à partir de sa valeur de et sa devise.
|
||||
* @param valeur valeur de la monnaie
|
||||
* @param devise devise de la monnaie
|
||||
*/
|
||||
public Monnaie(int valeur, String devise) {
|
||||
this.valeur = valeur;
|
||||
this.devise = devise;
|
||||
}
|
||||
|
||||
/** Obtenir la valeur de cette monnaie.
|
||||
* @param la valeur de cette monnaie
|
||||
*/
|
||||
public int getValeur() {
|
||||
return this.valeur;
|
||||
}
|
||||
|
||||
/** Obtenir la devise de cette monnaie.
|
||||
* @param la devise de cette monnaie
|
||||
*/
|
||||
public String getDevise() {
|
||||
return this.devise;
|
||||
}
|
||||
|
||||
/** Ajouter une autre monnaie à cette devise.
|
||||
* @param autre l'autre devise
|
||||
* @depend - <send> - DeviseInvalideException
|
||||
*/
|
||||
public void ajouter(Monnaie autre) throws DeviseInvalideException {
|
||||
verifierMemesDevises(autre);
|
||||
this.valeur += autre.valeur;
|
||||
}
|
||||
|
||||
/** Retrancher une autre monnaie à cette devise.
|
||||
* @param autre l'autre devise
|
||||
* @depend - <send> - DeviseInvalideException
|
||||
*/
|
||||
public void retrancher(Monnaie autre) throws DeviseInvalideException {
|
||||
verifierMemesDevises(autre);
|
||||
this.valeur -= autre.valeur;
|
||||
}
|
||||
|
||||
private void verifierMemesDevises(Monnaie autre) throws DeviseInvalideException {
|
||||
if (! this.devise.equals(autre.devise)) {
|
||||
throw new DeviseInvalideException("Devises incompatibles : "
|
||||
+ this.devise + " et " + autre.devise);
|
||||
}
|
||||
}
|
||||
|
||||
}
|
39
MonnaieTest.java
Normal file
39
MonnaieTest.java
Normal file
|
@ -0,0 +1,39 @@
|
|||
/** Classe regroupant les tests unitaires de la classe Monnaie. */
|
||||
public class MonnaieTest {
|
||||
|
||||
protected Monnaie m1;
|
||||
protected Monnaie m2;
|
||||
protected Monnaie m3;
|
||||
|
||||
@Avant
|
||||
public void debut() {
|
||||
this.m1 = new Monnaie(5, "euro");
|
||||
this.m2 = new Monnaie(7, "euro");
|
||||
}
|
||||
|
||||
@UnTest(enabled = false)
|
||||
public void ajouter() throws DeviseInvalideException {
|
||||
m1.ajouter(m2);
|
||||
Assert.assertTrue(m1.getValeur() == 12);
|
||||
}
|
||||
|
||||
@UnTest
|
||||
public void retrancher() throws DeviseInvalideException {
|
||||
m1.retrancher(m2);
|
||||
Assert.assertTrue(m1.getValeur() == -2);
|
||||
}
|
||||
|
||||
@UnTest(expected = NullPointerException.class)
|
||||
public void retrancher2() throws DeviseInvalideException {
|
||||
m1.retrancher(m2);
|
||||
m3.ajouter(m1);
|
||||
Assert.assertTrue(m1.getValeur() == 1234567890);
|
||||
}
|
||||
|
||||
@Apres
|
||||
public void rwwwwit() {
|
||||
this.m1 = null;
|
||||
this.m2 = null;
|
||||
}
|
||||
|
||||
}
|
12
MonnaieTest2.java
Normal file
12
MonnaieTest2.java
Normal file
|
@ -0,0 +1,12 @@
|
|||
/** MonnaieTest2 : Vérifier que les méthodes de test de la superclasse sont bien
|
||||
* prises en compte !
|
||||
* @author Xavier Crégut
|
||||
* @version $Revision$
|
||||
*/
|
||||
public class MonnaieTest2 extends MonnaieTest {
|
||||
|
||||
public void testSupplementaire() {
|
||||
// OK.
|
||||
}
|
||||
|
||||
}
|
9
UnTest.java
Normal file
9
UnTest.java
Normal file
|
@ -0,0 +1,9 @@
|
|||
import java.lang.annotation.*;
|
||||
|
||||
@Target(ElementType.METHOD)
|
||||
@Retention(RetentionPolicy.RUNTIME)
|
||||
public @interface UnTest {
|
||||
boolean enabled() default true;
|
||||
|
||||
Class<? extends Throwable> expected() default FausseException.class;
|
||||
}
|
Loading…
Reference in a new issue