Par défaut une transaction est démarrée au début de la 1ère méthode d'un bean CDI annotée par @Transactional, appelée par un backing bean. La transaction se termine à la fin de cette même méthode (même si d'autres méthodes du bean ont été appelées entre temps).
Pour qu'un transfert d'un compte à un autre se fasse dans une seule transaction, il suffit donc d'ajouter dans le bean une méthode dans laquelle on retire la somme du compte source et on ajoute cette somme dans le compte destination.
Ca serait une erreur d'appeler directement depuis le backing bean 2 méthodes du bean, une qui retire l'argent et l'autre qui ajoute l'argent (même si elles existent déjà), car le transfert se ferait alors avec 2 transactions, avec le risque d'un transfert effectué "à moitié".
La méthode du bean peut prendre en paramètre des CompteBancaire ou bien des id de CompteBancaire.
Pour le premier cas, les instances de CompteBancaire sont récupérées par le backing bean de la page, en dehors de la méthode du bean qui fait le transfert. A la fin de la méthode qui fait le transfert, il ne faut pas oublier d'enregistrer les modifications dans chacun des comptes avec la méthode merge, comme dans le TP1.
Dans le deuxième cas, cette méthode merge est inutile puisque les entités sont récupérées dans la même transaction et sont donc gérées par l'EntityManager jusqu'à la fin de la transaction. A la fin de la transaction, l'EntityManager va s'apercevoir que les entités ont été modifiées depuis qu'elles ont été récupérées au début de la transaction et il va donc enregistrer ces modifications dans la base de données (voir contexte de persistance dans le cours).
Vous allez choisir le premier cas car le deuxième ne convient pas bien pour afficher les messages d'erreur, par exemple si le solde du compte "source" est insuffisant, ou si un id n'existe pas. Dans le premier cas il est simple d'afficher ces messages d'erreur si les instances des comptes sont récupérées dans le backing bean qui a toutes les facilités JSF pour afficher ces messages d'erreur (voir la suite de ce TP).
Le code dans le bean (Premier cas)