IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Hibernate Java Discussion :

dé-synchronisation objet / table


Sujet :

Hibernate Java

Vue hybride

Message précédent Message précédent   Message suivant Message suivant
  1. #1
    Membre averti
    Homme Profil pro
    Développeur Web
    Inscrit en
    Mai 2002
    Messages
    15
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Somme (Picardie)

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : Administration - Collectivité locale

    Informations forums :
    Inscription : Mai 2002
    Messages : 15
    Par défaut dé-synchronisation objet / table
    Bonjour,
    je commence à passer une application web standard(jdbc) en hibernate3 et je suis confronté à un problème de dé-synchonisation entre les objets et les articles de la table .
    Je mets à jour un attribut d'objet avec le code suivant:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
     
            try
            {
                    Type typ = TypeDAO.instance.findType(id);
                    typ.setLibTyp(valeur);
                    TypeDAO.instance.saveOrUpdate(typ);
            }
            catch (Exception e)
            {
                     e.getMessage();
            }

    Or la valeur dépasse la taille du champ Oracle, j'ai donc le message Oracle d'erreur correspondant .
    L'objet affiché par l'application est , lui, quand même modifié , la table Oracle non .

    code de TypeDAO:

    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
     
        public Object saveOrUpdate(Object obj)  throws Exception
        {
            Session s = HibernateUtil.currentSession();
            Transaction tx = null;
            try
            {
                tx = s.beginTransaction();
                s.saveOrUpdate(obj);
                tx.commit();
            }
            catch (Exception e)
            {
                if (tx != null)
                {
                    System.out.println("saveOrUpdate.rollback");
                    tx.rollback();
                }
                throw e;
            }
            return obj;
        }
    Je pensais que la synchronisation était automatique . A moins que je l'utilise mal ,ce qui est bien possible .
    Je passe bien sur le rollback, j'ai un message pour le vérifier .

    Si quelqu'un a une idée, merci d'avance .

    Barny

  2. #2
    Membre averti
    Profil pro
    Inscrit en
    Février 2007
    Messages
    25
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 25
    Par défaut
    Salut,

    Tout ça me semble normal. Lorsqu'un objet se trouve dans la session hibernate, comme c'est le cas ici, et qu'il est modifié, hibernate s'en rend compte , et marque l'instance comme étant dirty. A un moment, hibernate va vouloir synchroniser sa session avec la base de données (on appelle ça le flush de session) et générer les ordres SQL correspondants. c'est à ce moment que les Exceptions SQL peuvent survenir.
    Dans le finally, c'est la transaction qui est rollbackée. Mais l'objet en mémoire n'est pas rollbacké : un rollback ne s'applique pas à des objets en mémoire.
    En conséquence, ton objet est toujours différent de son état en base oui.

    C'est ce mécanisme que l'on appelle synchronisation entre la session et la base : de la session vers la base.
    ça ne marche pas de la même façon dans l'autre sens.

    Sauf erreur de ma part maintenant, imaginons que l'objet en base est modifié pendant que ton code est exécuté : tu ne voudrais sans doute pas que ton objet en mémoire soit mis à jour sous peine de comportment bizarre! Donc hibernate ne synchronise pas en permanence l'état des objets avec leur image en base magiquement.

    Au final, dans ton cas, quand tu es confronté à une erreur SQL lors du flush de la session, il n'existe pas de rollback de l'état des objets, eh bien cela signifie que tu as un bug à corriger pour que cela ne se reproduise pas.

    En espérant que cela t'aide

  3. #3
    Membre averti
    Homme Profil pro
    Développeur Web
    Inscrit en
    Mai 2002
    Messages
    15
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Somme (Picardie)

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : Administration - Collectivité locale

    Informations forums :
    Inscription : Mai 2002
    Messages : 15
    Par défaut
    merci pour cette longue explication,

    Il suffit donc que je mette à jour mes objets mémoire dans mon catch ?

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
            try
            {
                    Type typ = TypeDAO.instance.findType(id);
                    typ.setLibTyp(valeur);
                    TypeDAO.instance.saveOrUpdate(typ);
            }
            catch (Exception e)
            {
                     listeType = TypeDAO.instance.findListType();
                     e.getMessage();
            }

  4. #4
    Membre averti
    Homme Profil pro
    Développeur Web
    Inscrit en
    Mai 2002
    Messages
    15
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Somme (Picardie)

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : Administration - Collectivité locale

    Informations forums :
    Inscription : Mai 2002
    Messages : 15
    Par défaut
    à priori ça ne suffit pas, j'ai procédé comme suit . Je sauvegarde la valeur avant et je la restaure si Exception .

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
     
            try
            {
                    Type typ = TypeDAO.instance.findType(id);
                    LibTyp=typ.getLibTyp();
                    typ.setLibTyp(valeur);
                    TypeDAO.instance.saveOrUpdate(typ);
            }
            catch (Exception e)
            {
                     typ.setLibTyp(LibTyp);
                     e.getMessage();
            }

  5. #5
    Inactif  
    Profil pro
    Inscrit en
    Mai 2006
    Messages
    2 189
    Détails du profil
    Informations personnelles :
    Âge : 45
    Localisation : Suisse

    Informations forums :
    Inscription : Mai 2006
    Messages : 2 189
    Par défaut
    Ca me parrait quand même super lourd, charger la liste complète pour ensuite effecuté un update, imagine que ta base est composé d'un million d'élément

    bon je connais pas de meilleure solution ...

    edit : Dans la doc d'hibernate partie 11.2.1. Non-managed environment

    http://www.hibernate.org/hib_docs/v3...nsactions.html

  6. #6
    Membre averti
    Profil pro
    Inscrit en
    Février 2007
    Messages
    25
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Février 2007
    Messages : 25
    Par défaut
    Je persiste à penser qu'il faudrait plutôt contrôler que l'objet est mis à jour conformément aux contraintes de la base, ie vérifier la taille de la String avant de la setter sur l'objet.

    Autrement, refaire une query ne suffit pas à rafraîchir l'objet car hibernate va ramener celui de son cache. Pour le forcer vraiment à le rafraichir par rapport à la base, il faut faire session.refresh(object) et l'objet sera réinitialisé par rapport à son état dans la base.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. [C# 1.1] Mémoriser un objet Table dans une session
    Par cpetitjean dans le forum ASP.NET
    Réponses: 4
    Dernier message: 20/09/2006, 16h38
  2. [Pl/SQL] relationnel objet : tables imbriquées
    Par gilux dans le forum Oracle
    Réponses: 1
    Dernier message: 18/03/2006, 00h23
  3. Réponses: 2
    Dernier message: 16/02/2006, 14h58
  4. Synchronisation de table
    Par Nic0tiN dans le forum Requêtes
    Réponses: 3
    Dernier message: 21/01/2006, 11h49
  5. [Relationnel Objet] Tables d'Objet et les OID
    Par Laurent Dardenne dans le forum Administration
    Réponses: 5
    Dernier message: 24/03/2004, 18h11

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo