[hibernate-issues] [Hibernate-JIRA] Commented: (HHH-2763) (lazy) m:n relation + EventListener = AssertionFailure: collection [n-side] was not processed by flush()

Jakob Braeuchi (JIRA) noreply at atlassian.com
Tue Nov 6 11:01:42 EST 2007


    [ http://opensource.atlassian.com/projects/hibernate/browse/HHH-2763?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel#action_28720 ] 

Jakob Braeuchi commented on HHH-2763:
-------------------------------------

hi c. delaloye,

based on your testcase i found a solution that works without modification to the hibernate code.  
i mark all CollectionEntries created by traversing the relationships as processed:


    public boolean onPreUpdate(PreUpdateEvent event) {
        Object entity = event.getEntity();
        System.out.println("-- Entering pre-update for " +
            entity.getClass().getName());
        
        Object[] oldValues = event.getOldState();
        String[] properties = event.getPersister().getPropertyNames();

        // Iterate through all fields of the updated object
        for (int ii = 0; ii < properties.length; ii++)
        {
            if (oldValues != null && oldValues[ii] instanceof Collection)
            {
                Collection col = (Collection) oldValues[ii];
                // Hibernate will initialize(load) the n:side of m:n collection,
                // but this will lead to following error later:
                // AssertionFailure:collection [n:side] was not processed
                // by flush()

                // get CollectionEntries before traversing the relationship
                List entriesBeforeLoad = new ArrayList();
                entriesBeforeLoad.addAll(event.getSource().getPersistenceContext()
                                .getCollectionEntries().values());

                // traverse the relationship and do some stuff
                for (Iterator iter = col.iterator(); iter.hasNext();)
                {
                    Object element = (Object) iter.next();
                    System.out.println(element);
                }

                // get CollectionEntries after traversing the relationship
                List entriesAfterLoad = new ArrayList();
                entriesAfterLoad.addAll(event.getSource().getPersistenceContext()
                                .getCollectionEntries().values());

                // keep CollectionEntries created by traversing and mark them as processed.
                entriesAfterLoad.removeAll(entriesBeforeLoad);
                Iterator iter = entriesAfterLoad.iterator();
                while (iter.hasNext())
                {
                    CollectionEntry ce = (CollectionEntry) iter.next();
                    ce.setProcessed(true);
                }
            }
        }
          
        System.out.println("-- Exiting pre-update for " +
                        entity.getClass().getName());
        return true;
    }

i'm not sure whether this causes any side-effects in your code. just give it a try.

greetings
jakob braeuchi

> (lazy) m:n relation + EventListener = AssertionFailure: collection [n-side] was not processed by flush()
> --------------------------------------------------------------------------------------------------------
>
>                 Key: HHH-2763
>                 URL: http://opensource.atlassian.com/projects/hibernate/browse/HHH-2763
>             Project: Hibernate3
>          Issue Type: Bug
>          Components: core
>    Affects Versions: 3.2.4.sp1, 3.2.5
>         Environment: Windows-XP, Jboss 4.2.1GA, Hibernate 3.2.4SP1, EJB3
>            Reporter: S.Schnabl
>            Priority: Critical
>         Attachments: bidirectional_many-to-many.gif, cdel_analyse.txt, HHH-2763_standalone_testcases.zip, one-to-many_with_many_side_having_collections.gif, Testcase.zip
>
>
> For more details see the attached testcase. I'm sorry, but in the short of time i only got a testcase for jboss-server 4.2. Please deploy the server.ear from /release-directory and then call the /src/client/TestCaseClient.java.
> [Summarized]
> It seems, that touching a lazy (Persistent-)Collection of at least a m:n relation inside a Hibernate event-listener always raises this error:
> org.hibernate.AssertionFailure: collection [n-side] was not processed by flush()
> [Explanation]
> I have two entities A. and B. Both having a m:n relation between each other. Furthermore there is an PostUpdateListener, which iterates onUpdate of entitiy through all properties of updated entity.
> [Testcase]
> Both entities are linked with eachother (m:n). If i  now do a simple update of a property of entity A --> MyPostUpdateListener will be called, which iterates through every property of the updated entity. In case of this property was a collection (= lazy PersistentCollection of m:n relation), hibernate initializes the collection for further work. I can now run through all objects of the collection, but after all work is done in listener, I get the following exception from postFlush:
> Caused by: org.hibernate.AssertionFailure: collection [com.qualitype.testcase.server.ejb.entity.EntityB.entitiesOfA] was not processed by flush()
> at org.hibernate.engine.CollectionEntry.postFlush(CollectionEntry.java:205)
> at org.hibernate.event.def.AbstractFlushingEventListener.postFlush(AbstractFlushingEventListener.java:333)
> at org.hibernate.event.def.DefaultFlushEventListener.onFlush(DefaultFlushEventListener.java:28)
> at org.hibernate.impl.SessionImpl.flush(SessionImpl.java:1000)
> at org.hibernate.impl.SessionImpl.managedFlush(SessionImpl.java:338)
> at org.hibernate.ejb.AbstractEntityManagerImpl$1.beforeCompletion(AbstractEntityManagerImpl.java:515)
> ... 29 more
> Attention: EntityB.entitiesOfA is the other-side  collection of the m:n relation of the updated EntityA.
> We are using hibernate-event listener system for auditing-purposes, so you should understand that touching every (element in the) collection is necessary for audit-purposes.
> Seems for me like a serious bug. Need this fixed asap ...

-- 
This message is automatically generated by JIRA.
-
If you think it was sent incorrectly contact one of the administrators: http://opensource.atlassian.com/projects/hibernate/secure/Administrators.jspa
-
For more information on JIRA, see: http://www.atlassian.com/software/jira

        



More information about the hibernate-issues mailing list