Bonjour a tous,
Je me suis pris une journée pour lire la doc hibernate sur des chapitres que je n'avais pas lu auparavant, comme entre autre le chapitre 10 ("Travailler avec des objets"), ainsi que le chapitre 11 ("Transactions et accès concurrents").
Je suis bien content d'avoir lu ces chapitres, plus d'autres, car je m'étais très mal habitué, notamment au niveau des méthodes à appeler sur les sessions, les transactions, etc... cependant il y'a quand meme qqe chose que je concois mal.
Ma question concerne les transactions et accès concurrents (Chapitre 11).
J'utilise des servlets pour le controle de la requete, les servlets remplissent des beans (persistance), une redirection à l'aide d'un request dispatcher est effectué sur une page JSP pour le rendu, bref un model MVC basic.
J'aimerai utiliser le pattern de transaction : session- par-requête-avec-objets-détachés.
En ce qui concerne le processus d'affaire ou l'unité de travail je me base sur la methode de la requete, ainsi pour doGet ou doPost, voici ou se trouve mes creations de session, ainsi que la création de la transaction et le commit :Un objet Session est relativement simple et n'est threadsafe. Il est également peu coûteux à créer. Il devrait n'être utilisé qu'une seule fois, pour un processus d'affaire ou une unité de travail ou une conversation et ensuite être relâché.
Ma première question :
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 public void doGet(HttpServletRequest req, HttpServletResponse res) throws IOException, ServletException { // UNE NOUVELLE SESSION EST CREE Session hibSession = HibernateUtil.currentSession(); Transaction tx = null; try { tx = hibSession.beginTransaction(); // LE TRAVAIL A EFFECTUE tx.commit(); } catch (Exception ex) { if (tx != null) tx.rollback(); throw new ServletException(ex); } finally { // LA SESSION EST FERME HibernateUtil.closeSession(); } }
Je pense que la création de la session en début et en fin de gestion de la requete est correct, en revanche, bien qu'il ne s'agisse pas d'un site web a forte concurrence, je me demande quand meme si la création de la transaction et son commit ne sont pas trop éloigné... J'ai lu qu'il est préferable que les requetes sql soit regroupé de la manière la plus atomique possible :
Mais en meme temps :Une transaction de base de données se doit d'être la plus courte possible afin de réduire les risques de collision sur des enregistrements verrouillés.
Ma deuxième question concerne les objets détachés, j'ai lu :Il est important de mentionner que d'utiliser un paradigme session-par-operation est un anti-pattern. Autrement dit: n'ouvrez et ne fermez pas la Session à chacun de vos accès simples à la base de données dans un même thread ! Bien sûr, le même raisonnement s'applique sur la gestion des transactions à la base de données.
J'aimerai utiliser cette méthode, mais voila je ne comprends pas comment on peut accéder au élément charger dans un doGet dans un doPost.Objets Détachés - Si vous décidez d'utiliser le paradigme session-par-requête discuté plus haut, toutes les entités chargées en mémoire deviendront des objets détachés durant le temps de réflexion de l'usager. Hibernate vous permet de rattacher ces objets et de persister les modifications y ayant été apportées. Ce pattern est appelé: session-per- request-with-detached-objects (littéralement: session- par-requête-avec-objets-détachés). Le versionnage automatique est utilisé afin d'isoler les modifications concurrentes.
(...)
Les objets détachés et le versionnage automatique :
Chaque interaction avec le système de persistance se fait via une nouvelle Session . Toutefois, les mêmes instances d'objets persistants sont réutilisées pour chacune de ces interactions. L'application doit pouvoir manipuler l'état des instances détachées ayant été chargées antérieurement via une autre session. Pour ce faire, ces objets persistants doivent être rattachés à la Session courante en utilisant Session.update() , Session.saveOrUpdate() , ou Session.merge() .
Je prends un exemple : Mon utilisateur clique sur une voiture dans une JSP, dans le doGet de la servlet correspondante je load cet voiture depuis la base de donnée grace a la méthode load() de session, mon objet voiture devient donc persistant, j'envoi ce bean rempli a une nouvelle JSP avec les valeurs du bean dans des textarea afin que l'utilisateur puisse par exemple modifier la couleur, la puissance de la voiture comme il le désire... utilisant le paradigme session-par-requete ma requete est biensure fermé a la fin du doGet, mon objet voiture devient donc détaché.
L'utilisateur appuie a ce moment sur envoyer les modifications, il arrive donc dans le doPost(), mais le doPost ne connait pas l'objet voiture... je ne peux donc pas l'update ! à moins que l'objet voiture soit une variable d'instance de ma servlet... ba oui mais dans ce cas la tous mes objets loadé dans le get devrait etre des variables d'instance de ma servlet, pire, si j'appel des fonctions dans le doGet() pour rendre ces objets persistants je devrait a toute leur passé mes variables d'instance en parametre... bref pas très propre.
Alors y'a qqe chose qui a du m'échapper dans la documentation sur les objets détachés, si qqun peut m'aider... Merci![]()
Partager