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 :

[hibernate] one-to-many et clé etrangère


Sujet :

Hibernate Java

  1. #1
    Membre actif
    Profil pro
    Inscrit en
    Avril 2006
    Messages
    370
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Avril 2006
    Messages : 370
    Points : 223
    Points
    223
    Par défaut
    Bonjour,

    Voilà, Hibernate me pose encore et toujours des soucis, en effet je n'arrive pas a mapper une relation one-to-many

    Contexte un utilisateur possède une collection (un set) de fichiers

    la table utilisateur :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    CREATE TABLE utilisateur
    (
      id int2 NOT NULL,
      nom varchar(20) NOT NULL,
      CONSTRAINT "User_pkey" PRIMARY KEY (id)
    ) 
    WITHOUT OIDS;
    ALTER TABLE utilisateur OWNER TO postgres;
    la table fichier :
    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
     
    CREATE TABLE fichiers
    (
      id int2 NOT NULL,
      nom varchar(50),
      id_utilisateur int2,
      CONSTRAINT fichiers_pkey PRIMARY KEY (id),
      CONSTRAINT fichiers_id_utilisateur_fkey FOREIGN KEY (id_utilisateur)
          REFERENCES utilisateur (id) MATCH SIMPLE
          ON UPDATE NO ACTION ON DELETE NO ACTION
    ) 
    WITHOUT OIDS;
    ALTER TABLE fichiers OWNER TO postgres;
    GRANT ALL ON TABLE fichiers TO postgres;
    GRANT ALL ON TABLE fichiers TO public;
    le mapping user :
    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
    <hibernate-mapping>
     
        <class name="metier.User" table="utilisateur">
     
            <id name="id" type="integer">
                 <column name="id"/>
                 <generator class="sequence" />
             </id>
     
            <property name="nom" type="string"> </property>
     
            <set name="fichiers" cascade="all" lazy="true">
                <key column="id_utilisateur"></key>
                <one-to-many class="metier.Fichier"></one-to-many>    
            </set>
     
        </class>
     
        </hibernate-mapping
    le test :
    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
    Session session = HibernateUtil.currentSession();
            Transaction tx = session.beginTransaction();
     
            User us = new User();
            us.setNom("Robert");
     
            Fichier fic1 = new Fichier();
            fic1.setNom("test.doc");
            Fichier fic2 = new Fichier();
            fic2.setNom("ouille.jpg");
     
            us.getFichiers().add(fic1);
            us.getFichiers().add(fic2);
            session.save(us);
     
            tx.commit();
     
            System.out.println("Enregistrement effectué");
            System.out.println("Recuperation des données");
     
            List listUser = session.createQuery("from utilisateur").list();
            Iterator it = listUser.iterator();
            while(it.hasNext())
            {
                User util = (User)it.next();
                System.out.println("L'utilisateur"+util.getNom()+"possède les fichiers suivants :");
                for(Fichier f : util.getFichiers())
                {
                    System.out.println(f.getNom());
                }
            }
     
            HibernateUtil.closeSession();
        }
    Et un extrait de l'erreur généré :
    Hibernate: select nextval ('hibernate_sequence')
    Hibernate: select nextval ('hibernate_sequence')
    Hibernate: select nextval ('hibernate_sequence')
    Hibernate: insert into utilisateur (nom, id) values (?, ?)
    Hibernate: insert into fichiers (nom, id_utilisateur, id) values (?, ?, ?)
    Hibernate: insert into fichiers (nom, id_utilisateur, id) values (?, ?, ?)
    15:00:16,409 WARN JDBCExceptionReporter:71 - SQL Error: 0, SQLState: null
    15:00:16,409 ERROR JDBCExceptionReporter:72 - L'élément du batch 0 insert into fichiers (nom, id_utilisateur, id) values (test.doc, 0, 54) a été annulé. Appeler getNextException pour en connaître la cause.
    15:00:16,409 WARN JDBCExceptionReporter:71 - SQL Error: 0, SQLState: 23503
    15:00:16,409 ERROR JDBCExceptionReporter:72 - ERROR: insert or update on table "fichiers" violates foreign key constraint "fichiers_id_utilisateur_fkey"
    Détail : Key (id_utilisateur)=(0) is not present in table "utilisateur".
    15:00:16,419 ERROR AbstractFlushingEventListener:300 - Could not synchronize database state with session
    org.hibernate.exception.ConstraintViolationException: Could not execute JDBC batch update
    Pourquoi prend-il 0 comme id utilisateur ? bizarre

    Voila toujours avec mes déboires face a Hibernate mais je suis têtu, j'y arriverai ...

    PS : si j'enlève la contrainte foreign key sur la colonne id_utilisateur de la table fichiers alors l'insertion marche. Mais la récupération foire sur :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    List listUser = session.createQuery("from utilisateur").list();
    avec l'erreur suivante :
    Exception in thread "main" java.lang.NoClassDefFoundError: antlr/ANTLRException
    at org.hibernate.hql.ast.ASTQueryTranslatorFactory.createQueryTranslator(ASTQueryTranslatorFactory.java:35)
    at org.hibernate.engine.query.HQLQueryPlan.<init>(HQLQueryPlan.java:72)
    at org.hibernate.engine.query.HQLQueryPlan.<init>(HQLQueryPlan.java:54)
    at org.hibernate.engine.query.QueryPlanCache.getHQLQueryPlan(QueryPlanCache.java:71)
    at org.hibernate.impl.AbstractSessionImpl.getHQLQueryPlan(AbstractSessionImpl.java:133)
    at org.hibernate.impl.AbstractSessionImpl.createQuery(AbstractSessionImpl.java:112)
    at org.hibernate.impl.SessionImpl.createQuery(SessionImpl.java:1583)
    at test.Test.main(Test.java:44)
    Quelqu'un saurait-il m'expliquer comment résoudre ce problème ?

    Merci d'avance pour votre aide.

  2. #2
    Membre régulier
    Profil pro
    Inscrit en
    Mars 2005
    Messages
    160
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2005
    Messages : 160
    Points : 75
    Points
    75
    Par défaut
    bonjour,

    enleve dans le fichier de mapping dans la definition de l'ID, le generator est dit moi ce qui se passe, j'avais à peu pres le meme probleme et j'essayer tout jusqu'à ce que j'enleve le generator surtout que les messages d'erreurs m'avaient brouillé un peu le chemin.
    donc essaie ça et reponds moi

  3. #3
    Membre éclairé

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Juillet 2002
    Messages
    346
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Consultant informatique

    Informations forums :
    Inscription : Juillet 2002
    Messages : 346
    Points : 737
    Points
    737
    Par défaut
    Salut,

    Quelques éléments/questions :
    - As-tu bien créé ta séquence (apparament, hibernate utilise une séquence appelé hibernate_sequence).
    - Quelle est la base de données que tu utilise : le generator sequence est pour oracle et postgres (de tête, à vérifier), mysql par exemple en utilise un autre
    - Précise le nom de ta séquence au niveau de la définition de ton générator c'est toujours mieux (regarde la doc hibernate).
    - La librairie antlr.jar est-elle bien dans ton classpath
    java.lang.NoClassDefFoundError: antlr/ANTLRException - Essaye de mettre dans ton hibernate.cfg.xml la propriété suivante celà désactive l'utilisation du batch de hibernate qui peut poser problème avec certaine version de base de données. De plus tu saura exactement où se situe ton problème les requête étant réalisé en temps réelle (en non en batch)
    <property name="hibernate.jdbc.batch_size">0</property>

  4. #4
    Membre actif
    Profil pro
    Inscrit en
    Avril 2006
    Messages
    370
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Avril 2006
    Messages : 370
    Points : 223
    Points
    223
    Par défaut
    J'utilise une base postgre 8.1, la sequence est bien défini dans la base.
    Précision : l'insertion d'un utilisateur seul sans fichier fonctionne, l'insertion d'un utilisateur avec des fichiers sans la contraine clé étrangère sur la colonne id_utilisateur de la table fichiers fonctionne.

    Mais pas moyen d'inserer ce même test qi la contrainte est placé sur la colonne id_utilisateur de la table fichiers.

    J'ai rajouter la librairie antlr mais cela ne solutionne pas le pb il me retourne toujours :
    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
    48
    49
    50
    51
    52
    53
    54
    55
    56
    57
     
    Exception in thread "main" org.hibernate.exception.ConstraintViolationException: could not insert: [metier.Fichier]
        at org.hibernate.exception.SQLStateConverter.convert(SQLStateConverter.java:71)
        at org.hibernate.exception.JDBCExceptionHelper.convert(JDBCExceptionHelper.java:43)
        at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2078)
        at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2427)
        at org.hibernate.action.EntityInsertAction.execute(EntityInsertAction.java:51)
        at org.hibernate.engine.ActionQueue.execute(ActionQueue.java:248)
        at org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:232)
        at org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:139)
        at org.hibernate.event.def.AbstractFlushingEventListener.performExecutions(AbstractFlushingEventListener.java:297)
        at org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:27)
        at org.hibernate.impl.SessionImpl.flush(SessionImpl.java:985)
        at org.hibernate.impl.SessionImpl.managedFlush(SessionImpl.java:333)
        at org.hibernate.transaction.JDBCTransaction.commit(JDBCTransaction.java:106)
        at test.Test.main(Test.java:39)
    Caused by: org.postgresql.util.PSQLException: ERROR: insert or update on table "fichiers" violates foreign key constraint "fichiers_id_utilisateur_fkey"
      Détail : Key (id_utilisateur)=(0) is not present in table "utilisateur".
        at org.postgresql.core.v3.QueryExecutorImpl.receiveErrorResponse(QueryExecutorImpl.java:1512)
        at org.postgresql.core.v3.QueryExecutorImpl.processResults(QueryExecutorImpl.java:1297)
        at org.postgresql.core.v3.QueryExecutorImpl.execute(QueryExecutorImpl.java:188)
        at org.postgresql.jdbc2.AbstractJdbc2Statement.execute(AbstractJdbc2Statement.java:430)
        at org.postgresql.jdbc2.AbstractJdbc2Statement.executeWithFlags(AbstractJdbc2Statement.java:346)
        at org.postgresql.jdbc2.AbstractJdbc2Statement.executeUpdate(AbstractJdbc2Statement.java:300)
        at org.hibernate.jdbc.NonBatchingBatcher.addToBatch(NonBatchingBatcher.java:23)
        at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2062)
        ... 11 more
    11:38:01,222  WARN JDBCExceptionReporter:71 - SQL Error: 0, SQLState: 23503
    11:38:01,222 ERROR JDBCExceptionReporter:72 - ERROR: insert or update on table "fichiers" violates foreign key constraint "fichiers_id_utilisateur_fkey"
      Détail : Key (id_utilisateur)=(0) is not present in table "utilisateur".
    11:38:01,222 ERROR AbstractFlushingEventListener:300 - Could not synchronize database state with session
    org.hibernate.exception.ConstraintViolationException: could not insert: [metier.Fichier]
        at org.hibernate.exception.SQLStateConverter.convert(SQLStateConverter.java:71)
        at org.hibernate.exception.JDBCExceptionHelper.convert(JDBCExceptionHelper.java:43)
        at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2078)
        at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2427)
        at org.hibernate.action.EntityInsertAction.execute(EntityInsertAction.java:51)
        at org.hibernate.engine.ActionQueue.execute(ActionQueue.java:248)
        at org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:232)
        at org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:139)
        at org.hibernate.event.def.AbstractFlushingEventListener.performExecutions(AbstractFlushingEventListener.java:297)
        at org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:27)
        at org.hibernate.impl.SessionImpl.flush(SessionImpl.java:985)
        at org.hibernate.impl.SessionImpl.managedFlush(SessionImpl.java:333)
        at org.hibernate.transaction.JDBCTransaction.commit(JDBCTransaction.java:106)
        at test.Test.main(Test.java:39)
    Caused by: org.postgresql.util.PSQLException: ERROR: insert or update on table "fichiers" violates foreign key constraint "fichiers_id_utilisateur_fkey"
      Détail : Key (id_utilisateur)=(0) is not present in table "utilisateur".
        at org.postgresql.core.v3.QueryExecutorImpl.receiveErrorResponse(QueryExecutorImpl.java:1512)
        at org.postgresql.core.v3.QueryExecutorImpl.processResults(QueryExecutorImpl.java:1297)
        at org.postgresql.core.v3.QueryExecutorImpl.execute(QueryExecutorImpl.java:188)
        at org.postgresql.jdbc2.AbstractJdbc2Statement.execute(AbstractJdbc2Statement.java:430)
        at org.postgresql.jdbc2.AbstractJdbc2Statement.executeWithFlags(AbstractJdbc2Statement.java:346)
        at org.postgresql.jdbc2.AbstractJdbc2Statement.executeUpdate(AbstractJdbc2Statement.java:300)
        at org.hibernate.jdbc.NonBatchingBatcher.addToBatch(NonBatchingBatcher.java:23)
        at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2062)
        ... 11 more
    Donc d'apres ce que j'en comprend il cherche a inserer les fichiers pour l'utilisateur d'id 0 qui bien sur n'existe pas ...
    Mais pourquoi agit t'il ainsi ??

  5. #5
    Membre éclairé

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Juillet 2002
    Messages
    346
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Consultant informatique

    Informations forums :
    Inscription : Juillet 2002
    Messages : 346
    Points : 737
    Points
    737
    Par défaut
    As tu essayer de mettre ça dans ton hibernate.cfg.xml?
    <property name="hibernate.jdbc.batch_size">0</property>

    Sinon, apparement il essaye de t'insérer fichier avant d'avoir executer la séquence.
    Essaye donc de faire un save sur ton user, puis ensuite de lui lier les fichier et de refaire un saveOrUpdate sur ton user

  6. #6
    Membre actif
    Profil pro
    Inscrit en
    Avril 2006
    Messages
    370
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Avril 2006
    Messages : 370
    Points : 223
    Points
    223
    Par défaut
    La propriete a été mise en effet,

    je vien de tester comme ca je ne sait pas si c'est ce que tu voulai faire
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
     
    User us = new User();
            us.setNom("Robert");
            session.save(us);
     
            Fichier fic1 = new Fichier();
            fic1.setNom("test.doc");
            Fichier fic2 = new Fichier();
            fic2.setNom("ouille.jpg");
     
            us.getFichiers().add(fic1);
            us.getFichiers().add(fic2);
     
            session.saveOrUpdate(us);
    Mais toutjours la même erreur ...

    Je commence a desespérer la cela fait maintenant 5jours que j'essai de faire fonctionner cet exemple tout simple avant de l'utiliser dans mon application (et vu qu'il s'agit de la persistance ca m'ennuie quand même beaucoup pour mon projet)

  7. #7
    Membre éclairé

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Juillet 2002
    Messages
    346
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Consultant informatique

    Informations forums :
    Inscription : Juillet 2002
    Messages : 346
    Points : 737
    Points
    737
    Par défaut
    Je te comprend. Je suis presque sur d'avoir eu la même erreur il y a deux ans, mais plus moyen de me rappeler comment la résoudre.

    Tu peut essayer de rajouter un session.flush() et un tx.commit() aprés le premier session.save(us).

  8. #8
    Membre actif
    Profil pro
    Inscrit en
    Avril 2006
    Messages
    370
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Avril 2006
    Messages : 370
    Points : 223
    Points
    223
    Par défaut
    Bon nouvelle erreur ce coup ci ...

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    Exception in thread "main" org.hibernate.TransactionException: Transaction not successfully started
        at org.hibernate.transaction.JDBCTransaction.commit(JDBCTransaction.java:100)
        at test.Test.main(Test.java:43)
    le code du main

    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
     
            Session session = HibernateUtil.currentSession();
            Transaction tx = session.beginTransaction();
     
     
     
            User us = new User();
            us.setNom("Jean");
            session.save(us);
            session.flush();
            tx.commit();
     
            Fichier fic1 = new Fichier();
            fic1.setNom("test.doc");
            Fichier fic2 = new Fichier();
            fic2.setNom("ouille.jpg");
     
            us.getFichiers().add(fic1);
            us.getFichiers().add(fic2);
     
            session.saveOrUpdate(us);
     
            tx.commit();
     
            System.out.println("Enregistrement effectué");
            System.out.println("Recuperation des données");
     
            List listUser = session.createQuery("from utilisateur").list();
            Iterator it = listUser.iterator();
            while(it.hasNext())
            {
                User util = (User)it.next();
                System.out.println("L'utilisateur"+util.getNom()+"possède les fichiers suivants :");
                for(Fichier f : util.getFichiers())
                {
                    System.out.println(f.getNom());
                }
            }
     
            HibernateUtil.closeSession();
    Donc malgrès l'exception, l'utilisateur est bien inséré, mais pas les fichiers ensuite ...

  9. #9
    Membre éclairé

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Juillet 2002
    Messages
    346
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Consultant informatique

    Informations forums :
    Inscription : Juillet 2002
    Messages : 346
    Points : 737
    Points
    737
    Par défaut
    Quelle est la ligne 43 de ta classe? (celle qui génère une erreur)

  10. #10
    Membre actif
    Profil pro
    Inscrit en
    Avril 2006
    Messages
    370
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Avril 2006
    Messages : 370
    Points : 223
    Points
    223
    Par défaut
    C'est le tx.commit() qui ne semble pas passer correctement (malgrès que l'enregistrement se fasse bien dans la base

  11. #11
    Membre éclairé

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Juillet 2002
    Messages
    346
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Consultant informatique

    Informations forums :
    Inscription : Juillet 2002
    Messages : 346
    Points : 737
    Points
    737
    Par défaut
    Le premier ou le deuxième tx.commit()? Si c'est le deuxième alors le comportement est normal (bien que je ne comprenne pas pourquoi ta transaction ne fonctionne pas)

    En fait, tu peut aussi essayer sans transaction (le risque dans ce cas là est d'avoir un User enregistré sans fichier), ou de placer des session.flush() avant ton session.saveOrUpdate();

  12. #12
    Membre actif
    Profil pro
    Inscrit en
    Avril 2006
    Messages
    370
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Avril 2006
    Messages : 370
    Points : 223
    Points
    223
    Par défaut
    Ba nan c'est bien lme premier tx.commit() qui pose problème ...

    Edit : nan c'est bien le deuxieme qui foire

    Si je rajoute le session.flush() avant le saveorupdate je me retrouve avec l'erreur d'avant (violation cle etrangere)

    C'est quand même pas possible, je veux utiliser hibernate pour avoir quelque chose de simple et élégant pour gérer ma base de donnée donc ca serait quand même bien qu'au final, je puisse l'utiliser de manière optimale sans trop de bidouille ou code a rallonge ...

    Aller aller on se motive pour m'aider (merci woodwai deja bien efficace aujourd'hui )

  13. #13
    Membre éclairé

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Juillet 2002
    Messages
    346
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Consultant informatique

    Informations forums :
    Inscription : Juillet 2002
    Messages : 346
    Points : 737
    Points
    737
    Par défaut
    Réellement je ne comprend pas, pour moi le premier code été déjà bon (avec un session.flush(); avant le tx.commit()
    C'est rageant quand même, ça fait deux ans que je fait de l'hibernate - je suis d'ailleur sure d'avoir déjà eu le problème - et pas moyen de trouver l'erreur.

    Enfin, peut-être quelqu'un d'autre avec un regard nouveau y arrivera.
    Bon courage en tout cas

  14. #14
    Membre actif
    Profil pro
    Inscrit en
    Avril 2006
    Messages
    370
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Avril 2006
    Messages : 370
    Points : 223
    Points
    223
    Par défaut
    Merci de ton aide en tout cas, sympa d'avoir l'espace d'un instant partagé ma galère avec hibernate

    Si des gens on des idées ....

  15. #15
    Membre éclairé Avatar de BizuR
    Profil pro
    Inscrit en
    Mai 2005
    Messages
    688
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France

    Informations forums :
    Inscription : Mai 2005
    Messages : 688
    Points : 757
    Points
    757
    Par défaut
    Tu peux redemarrer une autre transaction apres ton premier commit ?!? histoire de voir si ca passe bien... car normalement, une fois commitée, une transaction s'arrete.

    Ensuite, essaie de commiter également les fichiers créé pour que l'on soit sûrs que l'erreur vienne de la clé etrangere.

    Enfin, poste le bilan de tout ca et on verra plus loin pour analyser le problème

    EDIT : Tu as essayé d'oter la contrainte "not null" sur la clé etrangere pour voir ce que cela donnait ?
    Re-EDIT : De toute facon, tu n'as pas la contrainte ... donc bah n'essaie pas de l'oter

  16. #16
    Membre actif
    Profil pro
    Inscrit en
    Avril 2006
    Messages
    370
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Avril 2006
    Messages : 370
    Points : 223
    Points
    223
    Par défaut
    Alors : je n'est pas compris ce que tu entendais par
    Ensuite, essaie de commiter également les fichiers créé pour que l'on soit sûrs que l'erreur vienne de la clé etrangere
    Modifications du main :

    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
     
    Session session = HibernateUtil.currentSession();
            Transaction tx1 = session.beginTransaction();
     
     
     
            User us = new User();
            us.setNom("Jean");
            session.save(us);
     
            tx1.commit();
     
            Transaction tx2 = session.beginTransaction();
     
            Fichier fic1 = new Fichier();
            fic1.setNom("test.doc");
            Fichier fic2 = new Fichier();
            fic2.setNom("ouille.jpg");
     
            us.getFichiers().add(fic1);
            us.getFichiers().add(fic2);
     
            session.flush();
            session.saveOrUpdate(us);
     
            tx2.commit();
    Et toujours le même type d'erreurs générées :

    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
     
    Hibernate: select nextval ('hibernate_sequence')
    Hibernate: insert into utilisateur (nom, id) values (?, ?)
    Hibernate: select nextval ('hibernate_sequence')
    Hibernate: select nextval ('hibernate_sequence')
    Hibernate: insert into fichiers (nom, id_utilisateur, id) values (?, ?, ?)
    10:36:12,081  WARN JDBCExceptionReporter:71 - SQL Error: 0, SQLState: 23503
    10:36:12,081 ERROR JDBCExceptionReporter:72 - ERROR: insert or update on table "fichiers" violates foreign key constraint "fichiers_id_utilisateur_fkey"
      Détail : Key (id_utilisateur)=(0) is not present in table "utilisateur".
    10:36:12,081 ERROR AbstractFlushingEventListener:300 - Could not synchronize database state with session
    org.hibernate.exception.ConstraintViolationException: could not insert: [metier.Fichier]
        at org.hibernate.exception.SQLStateConverter.convert(SQLStateConverter.java:71)
        at org.hibernate.exception.JDBCExceptionHelper.convert(JDBCExceptionHelper.java:43)
        at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2078)
        at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2427)
        at org.hibernate.action.EntityInsertAction.execute(EntityInsertAction.java:51)
        at org.hibernate.engine.ActionQueue.execute(ActionQueue.java:248)
        at org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:232)
        at org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:139)
        at org.hibernate.event.def.AbstractFlushingEventListener.performExecutions(AbstractFlushingEventListener.java:297)
        at org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:27)
        at org.hibernate.impl.SessionImpl.flush(SessionImpl.java:985)
        at test.Test.main(Test.java:43)
    Caused by: org.postgresql.util.PSQLException: ERROR: insert or update on table "fichiers" violates foreign key constraint "fichiers_id_utilisateur_fkey"
      Détail : Key (id_utilisateur)=(0) is not present in table "utilisateur".
        at org.postgresql.core.v3.QueryExecutorImpl.receiveErrorResponse(QueryExecutorImpl.java:1512)
        at org.postgresql.core.v3.QueryExecutorImpl.processResults(QueryExecutorImpl.java:1297)
        at org.postgresql.core.v3.QueryExecutorImpl.execute(QueryExecutorImpl.java:188)
        at org.postgresql.jdbc2.AbstractJdbc2Statement.execute(AbstractJdbc2Statement.java:430)
        at org.postgresql.jdbc2.AbstractJdbc2Statement.executeWithFlags(AbstractJdbc2Statement.java:346)
        at org.postgresql.jdbc2.AbstractJdbc2Statement.executeUpdate(AbstractJdbc2Statement.java:300)
        at org.hibernate.jdbc.NonBatchingBatcher.addToBatch(NonBatchingBatcher.java:23)
        at org.hibernate.persister.entity.AbstractEntityPersister.insert(AbstractEntityPersister.java:2062)
        ... 9 more

  17. #17
    Membre éclairé Avatar de BizuR
    Profil pro
    Inscrit en
    Mai 2005
    Messages
    688
    Détails du profil
    Informations personnelles :
    Âge : 42
    Localisation : France

    Informations forums :
    Inscription : Mai 2005
    Messages : 688
    Points : 757
    Points
    757
    Par défaut
    en gros, je voulais que tu fasses ainsi :

    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
     
     Session session = HibernateUtil.currentSession();
             Transaction tx = session.beginTransaction();
             System.out.println("Creation User");
             User us = new User();
             us.setNom("Jean");
             session.save(us);
     
             tx.commit();
    tx = session.beginTransaction();
             System.out.println("Creation Fichiers");
             Fichier fic1 = new Fichier();
             fic1.setNom("test.doc");
             Fichier fic2 = new Fichier();
             fic2.setNom("ouille.jpg");
     
    tx.commit();
    tx = session.beginTransaction();
     
    //si tout s'enregistre alors ce la vient bien de ton association qui s'enregistre mal. 
    System.out.println("Creation Liaisons");
             us.getFichiers().add(fic1);
             us.getFichiers().add(fic2);
     
    /*ici, ces deux lignes font double emploi ... un flush() sauvegarde déjà les éléments modifiés dans la base ... donc le saveOrUpdate n'est pas necessaire*/
             session.flush();
             //session.saveOrUpdate(us);
     
             tx.commit();
    EDIT: Essaie aussi d'afficher les ID de ton user pour voir ce que cela donne (juste avant le flush())

  18. #18
    Membre actif
    Profil pro
    Inscrit en
    Avril 2006
    Messages
    370
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Avril 2006
    Messages : 370
    Points : 223
    Points
    223
    Par défaut
    Alors : toujours la même erreur ...

    Lorsque j'affiche l'id de mon utilisateur juste avant le flush, il me retourne bien la bonne valeur donc en effet cela doit bien etre le mapping qui ne va pas.

    Voici donc le mapping que j'ai fait pour lié fichiers et utilisateur :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    <set name="fichiers" cascade="all" lazy="true">
                <key column="id_utilisateur"></key>
                <one-to-many class="metier.Fichier"></one-to-many>    
            </set>
    Où id_utilisateur c'est le nom du champ clé etrangère de la table fichier

  19. #19
    Membre éclairé

    Homme Profil pro
    Consultant informatique
    Inscrit en
    Juillet 2002
    Messages
    346
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Nord (Nord Pas de Calais)

    Informations professionnelles :
    Activité : Consultant informatique

    Informations forums :
    Inscription : Juillet 2002
    Messages : 346
    Points : 737
    Points
    737
    Par défaut
    Moi ce qui m'inquiète c'est :
    AbstractFlushingEventListener:300 - Could not synchronize database state with session
    Celà ressemble à un problème de base de données. Un problème de synchronisation.
    Utilises-tu une datasource ou une connexion directe à la base de données?

  20. #20
    Membre actif
    Profil pro
    Inscrit en
    Avril 2006
    Messages
    370
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Avril 2006
    Messages : 370
    Points : 223
    Points
    223
    Par défaut
    Je pense qu'il marque cela quand il y as un problème avec la base de données (sur la structure, les contraintes ...). J'avais deja eu ce message lors d'un problème avec une table.

Discussions similaires

  1. Problème hibernate one-to-many / many-to-one
    Par valkeke dans le forum Hibernate
    Réponses: 4
    Dernier message: 02/04/2014, 15h06
  2. Mapping Hibernate one-to-many
    Par [ric] dans le forum Hibernate
    Réponses: 1
    Dernier message: 16/09/2010, 12h04
  3. [Hibernate] Relation one to many
    Par BRAUKRIS dans le forum Hibernate
    Réponses: 2
    Dernier message: 23/08/2006, 12h51
  4. [Hibernate][one-to-one] clé etrangère avec des blancs
    Par seb_fou dans le forum Hibernate
    Réponses: 1
    Dernier message: 06/04/2006, 11h28
  5. [hibernate] relation one-to-many avec plusieurs clés
    Par seb_fou dans le forum Hibernate
    Réponses: 6
    Dernier message: 16/03/2006, 15h47

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