Bonjour à tous,
j'ai une suite de test JUnit 4 qui utilisent Spring (classes annotées par @RunWith(SpringJUnit4ClassRunner.class)).
J'ai différents package de tests : un pour les dao, un pour les services, et un pour les pages web. Le contexte n'est pas le même en fonction du package : pour le package de test des pages, la base de données et initialisée, pour les autres non.
Quand je lance les tests package par package, aucun problème, tous les tests passent. Par contre, quand je lance l'ensemble des tests d'un coup, l'une de mes classes de tests ne passe plus.
Appelons TestPage cette classe de test qui ne marche plus. Comme son nom l'indique, cette classe de Test appartient au package des pages, et donc la base de données doit être initialisée. Voici le setup de TestPage :
Les tests qui suivent ne passent pas car benji est null, alors que dans le fichier de conf, la base de données est censé être initialisée.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35 @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration("/applicationContext.xml") @DirtiesContext public class TestPage { protected WicketTester tester; @Autowired private ApplicationContext applicationContext; @Autowired private ServiceMembre serviceMembre; private Membre benji; private SessionE4N session; @Before public void setup(){ tester = new WicketTester(new WicketApplication(){ @Override protected SpringComponentInjector getSpringInjector() { return new SpringComponentInjector(this, applicationContext, true); } }); //recuperation de benji dans la BD benji = serviceMembre.getOne("ben.joris"); tester.setupRequestAndResponse(); //on recupere la session et on insere Benji dedans pour pouvoir tester les pages de l'espace membre session = SessionE4N.get(); session.setMembre(benji); } ... }
appelons TestDao le test qui passe juste avant TestPage dans la suite des tests. Comme son nom l'indique, cette classe de tests appartient au package DAO et n'utilise donc pas le même contexte de base que TestPage. Dans cette classe, chaque test est inclu dans une transaction. Voici les méthodes setup et teardown de TestDao :
En investiguant, j'ai remarqué qu'en supprimant l'annotation @AfterTransaction, les test de TestPage sont Ok.
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47 @RunWith(SpringJUnit4ClassRunner.class) @ContextConfiguration("TestDao-context.xml") @DirtiesContext @Transactional public class TestDao { @Autowired private ReponseDao reponseDao; @Autowired private ServiceQuestionnaire serviceQuestionnaire; @Autowired private ServiceMembre serviceMembre; private Membre benji; private Reponse reponse; private Questionnaire q1; @BeforeTransaction public void startTransaction() throws ParseException{ benji = new Membre(); benji.setIdentifiant("ben.joris"); q1 = new Questionnaire(); q1.setNumero("Q1"); q1 = serviceQuestionnaire.saveOne(q1); reponse = new Reponse(); reponse.setNumReponse(1); reponse.setReponse("reponse 1"); //Mise à jour des références reponse.setMembre(benji); reponse.setQuestionnaire(q1); q1.getListeReponses().add(reponse); benji.getListeReponses().add(reponse); //Persistence du membre et des réponses associées benji = serviceMembre.saveOne(benji); reponse = reponseDao.getOne(benji.getListeReponses().get(0).getIdReponse()); } @AfterTransaction public void afterTransaction(){ serviceMembre.deleteOne(benji); serviceQuestionnaire.deleteOne(q1); }
Il y a donc visiblement un problème dans le nettoyage du contexte entre les deux classes de tests. Je croyais pourtant que l'annotation @DirtiesContext forçait spring à recharger le contexte pour les tests de la classe suivante. Mais visiblement, ce n'est pas ce qui se passe ici.
Il y a une subtilité qui m'échappe, j'espère que quelqu'un pourra éclairer ma lanterne sur le pourquoi du comment...
Merci d'avance !
Partager