-->
These old forums are deprecated now and set to read-only. We are waiting for you on our new forums!
More modern, Discourse-based and with GitHub/Google/Twitter authentication built-in.

All times are UTC - 5 hours [ DST ]



Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 5 posts ] 
Author Message
 Post subject: Collection Dirty! Hibernate keeps deleting and inserting
PostPosted: Thu Nov 02, 2006 2:32 pm 
Newbie

Joined: Fri Jun 23, 2006 9:25 am
Posts: 10
Ok. I have this collection which implemented using a mapping/association table. This table has an extra column which stores the order of the associated objects.

I have a problem with hibernate always thinking my collection is dirty and deleting it and reinserting it. This happens every time I attempt to load the object. So, when I load Chapter where id=1 the set of pages is loaded, determined to be dirty, deleted from the association table, reinserted into the association table, and reinserted into the object.

I've looked at: http://www.hibernate.org/116.html#A15 the object's getter/setter methods are as simple as they can get.

Any help anyone could offer would be exceptional. I'm at my wits end.

Here is the output from the log:
Code:
NFO - Loading the object from the db based on param.id:1
DEBUG - Opening Hibernate Session
DEBUG - opened session at timestamp: 4761563160371200
DEBUG - loading entity: [com.hdms.rdesigner.domain.chapter.Chapter#1]
DEBUG - attempting to resolve: [com.hdms.rdesigner.domain.chapter.Chapter#1]
DEBUG - object not resolved in any cache: [com.hdms.rdesigner.domain.chapter.Chapter#1]
DEBUG - Fetching entity: [com.hdms.rdesigner.domain.chapter.Chapter#1]
DEBUG - loading entity: [com.hdms.rdesigner.domain.chapter.Chapter#1]
DEBUG - about to open PreparedStatement (open PreparedStatements: 0, globally: 0)
DEBUG - opening JDBC connection
[b]DEBUG - /* load com.hdms.rdesigner.domain.chapter.Chapter [/b]*/ select chapter0_.id as id0_0_, chapter0_.name as name0_0_, chapter0_.shortName as shortName0_0_, chapter0_.description as descript4_0_0_ from Chapters chapter0_ where chapter0_.id=?
DEBUG - preparing statement
DEBUG - binding '1' to parameter: 1
DEBUG - about to open ResultSet (open ResultSets: 0, globally: 0)
DEBUG - processing result set
DEBUG - result set row: 0
DEBUG - result row: EntityKey[com.hdms.rdesigner.domain.chapter.Chapter#1]
DEBUG - Initializing object from ResultSet: [com.hdms.rdesigner.domain.chapter.Chapter#1]
DEBUG - Hydrating entity: [com.hdms.rdesigner.domain.chapter.Chapter#1]
DEBUG - returning 'a' as column: name0_0_
DEBUG - returning 'a' as column: shortName0_0_
DEBUG - returning '' as column: descript4_0_0_
DEBUG - done processing result set (1 rows)
DEBUG - about to close ResultSet (open ResultSets: 1, globally: 1)
DEBUG - about to close PreparedStatement (open PreparedStatements: 1, globally: 1)
DEBUG - closing statement
DEBUG - total objects hydrated: 1
DEBUG - resolving associations for [com.hdms.rdesigner.domain.chapter.Chapter#1]
DEBUG - creating collection wrapper:[com.hdms.rdesigner.domain.chapter.Chapter.pages#1]
DEBUG - initializing collection [com.hdms.rdesigner.domain.chapter.Chapter.pages#1]
DEBUG - checking second-level cache
DEBUG - collection not cached
DEBUG - loading collection: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1]
DEBUG - about to open PreparedStatement (open PreparedStatements: 0, globally: 0)
DEBUG - /* load collection com.hdms.rdesigner.domain.chapter.Chapter.pages */ select pages0_.ChapterId as ChapterId1_, pages0_.PageOrder as PageOrder1_, pages0_.pageId as pageId1_, page1_.id as id6_0_, page1_.name as name6_0_, page1_.shortName as shortName6_0_, page1_.description as descript4_6_0_ from ChapterPageMap pages0_ inner join Pages page1_ on pages0_.pageId=page1_.id where pages0_.ChapterId=? order by pages0_.PageOrder
DEBUG - preparing statement
DEBUG - binding '1' to parameter: 1
DEBUG - about to open ResultSet (open ResultSets: 0, globally: 0)
DEBUG - result set contains (possibly empty) collection: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1]
DEBUG - uninitialized collection: initializing
DEBUG - processing result set
DEBUG - result set row: 0
DEBUG - returning '2' as column: id6_0_
DEBUG - result row: EntityKey[com.hdms.rdesigner.domain.page.Page#2]
DEBUG - Initializing object from ResultSet: [com.hdms.rdesigner.domain.page.Page#2]
DEBUG - Hydrating entity: [com.hdms.rdesigner.domain.page.Page#2]
DEBUG - returning 'b' as column: name6_0_
DEBUG - returning 'b' as column: shortName6_0_
DEBUG - returning 'a' as column: descript4_6_0_
DEBUG - returning '1' as column: ChapterId1_
DEBUG - found row of collection: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1]
DEBUG - reading row
DEBUG - returning '1' as column: PageOrder1_
DEBUG - returning '2' as column: pageId1_
DEBUG - loading entity: [com.hdms.rdesigner.domain.page.Page#2]
DEBUG - attempting to resolve: [com.hdms.rdesigner.domain.page.Page#2]
DEBUG - resolved object in session cache: [com.hdms.rdesigner.domain.page.Page#2]
DEBUG - done processing result set (1 rows)
DEBUG - about to close ResultSet (open ResultSets: 1, globally: 1)
DEBUG - about to close PreparedStatement (open PreparedStatements: 1, globally: 1)
DEBUG - closing statement
DEBUG - total objects hydrated: 1
DEBUG - resolving associations for [com.hdms.rdesigner.domain.page.Page#2]
DEBUG - done materializing entity [com.hdms.rdesigner.domain.page.Page#2]
DEBUG - 1 collections were found in result set for role: com.hdms.rdesigner.domain.chapter.Chapter.pages
DEBUG - collection fully initialized: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1]
DEBUG - 1 collections initialized for role: com.hdms.rdesigner.domain.chapter.Chapter.pages
DEBUG - done loading collection
DEBUG - collection initialized
DEBUG - done materializing entity [com.hdms.rdesigner.domain.chapter.Chapter#1]
DEBUG - initializing non-lazy collections
DEBUG - done entity load
DEBUG - after autocommit
DEBUG - transaction completed on session with on_close connection release mode; be sure to close the session to release JDBC resources!
DEBUG - after transaction completion
DEBUG - Eagerly flushing Hibernate session
DEBUG - flushing session
DEBUG - processing flush-time cascades
[b]DEBUG - dirty checking collections
DEBUG - Collection dirty: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1][/b]
DEBUG - Flushing entities and processing referenced collections
DEBUG - Wrapped collection in role: com.hdms.rdesigner.domain.chapter.Chapter.pages
DEBUG - Collection found: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1], was: [<unreferenced>] (initialized)
DEBUG - Processing unreferenced collections
DEBUG - Collection dereferenced: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1]
DEBUG - Scheduling collection removes/(re)creates/updates
DEBUG - Flushed: 0 insertions, 0 updates, 0 deletions to 2 objects
DEBUG - Flushed: 1 (re)creations, 0 updates, 1 removals to 2 collections
DEBUG - listing entities:
DEBUG - com.hdms.rdesigner.domain.chapter.Chapter{pages=[component[order,page]{page=com.hdms.rdesigner.domain.page.Page#2, order=1}], shortName=a, description=, name=a, id=1}
DEBUG - com.hdms.rdesigner.domain.page.Page{shortName=b, description=a, name=b, id=2}
DEBUG - executing flush
DEBUG - registering flush begin
DEBUG - Deleting collection: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1]
DEBUG - about to open PreparedStatement (open PreparedStatements: 0, globally: 0)
[b]DEBUG - /* delete collection com.hdms.rdesigner.domain.chapter.Chapter.pages */ delete from ChapterPageMap where ChapterId=?[/b]DEBUG - preparing statement
DEBUG - binding '1' to parameter: 1
DEBUG - Adding to batch
DEBUG - done deleting collection
DEBUG - Executing batch size: 1
DEBUG - about to close PreparedStatement (open PreparedStatements: 1, globally: 1)
DEBUG - closing statement
DEBUG - Inserting collection: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1]
DEBUG - about to open PreparedStatement (open PreparedStatements: 0, globally: 0)
[b]DEBUG - /* insert collection row com.hdms.rdesigner.domain.chapter.Chapter.pages */ insert into ChapterPageMap (ChapterId, PageOrder, pageId) values (?, ?, ?)[/b]DEBUG - preparing statement
DEBUG - binding '1' to parameter: 1
DEBUG - binding '1' to parameter: 2
DEBUG - binding '2' to parameter: 3
DEBUG - Adding to batch
DEBUG - done inserting collection: 1 rows inserted
DEBUG - Executing batch size: 1
DEBUG - about to close PreparedStatement (open PreparedStatements: 1, globally: 1)
DEBUG - closing statement
DEBUG - registering flush end
DEBUG - post flush
DEBUG - Closing Hibernate Session



Here's my Entity/Object Hibernate mapping
Code:
    <class name="com.hdms.rdesigner.domain.chapter.Chapter" table="Chapters"
        lazy="false" dynamic-update="true">

        <id name="id" type="long" unsaved-value="null">
            <generator class="native" />
        </id>
        <property name="name" />       
        <property name="shortName" />
        <property name="description" />

<set name="pages" table="ChapterPageMap" lazy="false" cascade="none"  order-by="PageOrder">          
  <key column="ChapterId"/>
   <composite-element class="com.hdms.rdesigner.domain.chapterpage.ChapterPage">
       <property name="order" column="PageOrder" type="long" />
       <many-to-one name="page" column="pageId" class="com.hdms.rdesigner.domain.page.Page" not-null="true"/>
   </composite-element>
</set>
</class>

My Java Class File looks like:
Code:
public class Chapter extends AbstractPlanRelationshipBean{

   protected Set<Packet> packets;
   protected Set<Page> pages;
     
   //For hibernate...
   public Chapter() {}
    public Chapter(ChapterForm form) {
       id = form.getId();
      name = form.getName();
      shortName = form.getShortName();
      description = form.getDescription();
      plan = form.getPlan();
      pages = form.getPages();
    }
   
   /*-------------------------------*/
    public Set<Packet> getPackets() {
       return packets;
    }
   public void setPackets(Set<Packet> val) {
      packets = val;
   }
   public void addPacket(Packet val) {
      packets.add(val);
   }
   
   /*-------------------------------*/
    public Set<Page> getPages() {
       return pages;
    }
    public void setPages(Collection <Page> val) {
       pages = new LinkedHashSet(val);
    }
    public void addPage(Page val) {
      pages.add(val);
   }
   
    /*-------------------------------*/
    public void setOrderOfSets() {
       
       //We only care about the pages
       Iterator it =  getPages().iterator();
       for(int i=1; it.hasNext(); i++) {
          Page p = (Page)it.next();
          p.setOrder(new Long(i));
       }
    }
   
    /*-------------------------------*/
    public String toString() {
       String result = super.toString();
       
       if( packets != null) {
          result += " Packets Size: " + packets.size();
       }
       if( pages != null) {
          result += " Pages Size: " + pages.size();
       }
       
       return result;
    }
}


The Table Structure is as follows:
Code:
DROP TABLE IF EXISTS ChapterPageMap ;
CREATE TABLE ChapterPageMap
(
        Id INTEGER NOT NULL AUTO_INCREMENT,
        ChapterId INTEGER NOT NULL REFERENCES Chapters(Id),
        PageId INTEGER NOT NULL REFERENCES Pages(Id),
        PageOrder INTEGER,
        LastEdited TIMESTAMP,
        UNIQUE INDEX1 (ChapterId, PageId),
        PRIMARY KEY (Id)
)ENGINE=InnoDB;


Top
 Profile  
 
 Post subject:
PostPosted: Fri Nov 03, 2006 1:58 am 
Regular
Regular

Joined: Tue May 16, 2006 3:32 am
Posts: 117
Avoid doing this:

pages = new LinkedHashSet(val);


Quote:
Code:

   public void setPages(Collection <Page> val) {
        pages = new LinkedHashSet(val);
    }



Top
 Profile  
 
 Post subject: Well
PostPosted: Fri Nov 03, 2006 10:32 am 
Newbie

Joined: Fri Jun 23, 2006 9:25 am
Posts: 10
I wish that had solved the problem. You did find the error for me. Unfortunately it's still behaving the same way. There is a slight difference in the log output though:

Code:
DEBUG - Collection dirty: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1]
DEBUG - Flushing entities and processing referenced collections
DEBUG - Collection found: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1], was: [com.hdms.rdesigner.domain.chapter.Chapter.pages#1] (initialized)
DEBUG - Processing unreferenced collections



I would like to figure out a solution for this without having to create a Mapping class/object just for holding the association... but I might just have to go that route.


Top
 Profile  
 
 Post subject:
PostPosted: Tue Nov 21, 2006 9:18 am 
Newbie

Joined: Tue Nov 21, 2006 8:57 am
Posts: 1
I had a similar problem with <composite-element> doing pointless delete and inserts. After many hours of searching, I managed to find one line in the hibernate reference that helped me solve it.

http://www.hibernate.org/hib_docs/reference/en/html/components.html#components-incollections

Quote:
Note: if you define a Set of composite elements, it is very important to implement equals() and hashCode() correctly.


After I implementing equals() and hashCode() on my association class, the unwanted deleting and inserting stopped.

In your case I believe that you should implement equals() and hashCode() properly on your 'com.hdms.rdesigner.domain.chapterpage.ChapterPage' class.

I hope this helps.

Here is a link that helped me with my investigation:
http://opensource.atlassian.com/projects/hibernate/browse/HB-124


Top
 Profile  
 
 Post subject: similar problem
PostPosted: Mon Feb 04, 2008 7:54 am 
Newbie

Joined: Mon Feb 04, 2008 7:42 am
Posts: 7
I have been an experiencing a similar issue.

Implementing equals() and hashcode() on the association class seems to have done the trick.

However, if I implement equals/hashcode on the class at the end of the many-many association I break it again. I.e. i have a many to many association Person->Language with the LanguageLink as the join table.

No hashcode/equals on any classes - doesn't work
-----------------------------------------------------------
Person
LanguageLink
Language

hashcode/equals on association - works
------------------------------------
Person
LanguageLink - implemented hashcode() equals()
Language

hashcode equals/on both - broken again!
--------------------------------
Person
LanguageLink - implemented hashcode() equals()
Language - implemented hashcode() equals

This isn't a major problem but I'm curious as to why having the hashcode/equals on both breaks it!

Any ideas?


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 5 posts ] 

All times are UTC - 5 hours [ DST ]


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum

Search for:
© Copyright 2014, Red Hat Inc. All rights reserved. JBoss and Hibernate are registered trademarks and servicemarks of Red Hat, Inc.