I created a test case with a self-contained example:
http://216.121.112.228/browse/NH-2727.


On May 23, 2:54 pm, Ricardo Peres <[email protected]> wrote:
> Tried with both NH 3.1 and the trunk, same behavior.
>
> On May 23, 2:27 pm, Ricardo Peres <[email protected]> wrote:
>
>
>
>
>
>
>
> > Here is the actual test:
>
> > using (ISession session = sessionFactory.OpenSession())
> >                                 {
> >                                         UserGroup ug = 
> > session.CreateQuery("from UserGroup where
> > User.UsrId = 1").UniqueResult<UserGroup>();
> >                                         User u = ug.User;
>
> >                                         bool d1 = 
> > session.IsChanged(ug);//Fabio's code
> >                                         bool d2 = session.IsChanged(u);
>
> >                                         Debug.Assert(ug.User == u);
>
> >                                         Debug.Assert(session.IsDirty() == 
> > false);
> >                                         session.Flush();
> >                                 }
>
> >                                 using (ISession session = 
> > sessionFactory.OpenSession())
> >                                 {
> >                                         User u = session.CreateQuery("from 
> > User where id =
> > 1").UniqueResult<User>();
> >                                         UserGroup ug = u.UserGroup.First();
>
> >                                         bool d1 = session.IsChanged(ug);
> >                                         bool d2 = session.IsChanged(u);
>
> >                                         Debug.Assert(ug.User == u);
>
> >                                         Debug.Assert(session.IsDirty() == 
> > false);//fires SaveOrUpdate
> > event
> >                                         session.Flush();
> >                                 }
>
> > On May 23, 12:48 pm, Ricardo Peres <[email protected]> wrote:
>
> > > Forgot to tell: I am using HiLo for ids and, of course, I am not
> > > changing anything on any of the loaded entities. No second level cache
> > > either.
>
> > > On May 23, 12:43 pm, Ricardo Peres <[email protected]> wrote:
>
> > > > Hi,
>
> > > > I am having this problem:
>
> > > > - I load a User entity from the DB using session.Get<T>();
> > > > - It loads an additional collection UserGroups containing only one
> > > > entity;
> > > > - I have an event listener for the SaveOrUpdate event:
>
> > > > cfg.EventListeners.SaveOrUpdateEventListeners =
> > > > cfg.EventListeners.SaveOrUpdateEventListeners.Concat(new[] { new
> > > > AuditableListener() }).ToArray();
>
> > > > - I check that both entities are not changed, using Fabio's code:
>
> > > > private bool HasDirtyProperties(FlushEntityEvent @event)
> > > >     {
> > > >         ISessionImplementor session = @event.Session;
> > > >         EntityEntry entry = @event.EntityEntry;
> > > >         var entity = @event.Entity;
> > > >         if(!entry.RequiresDirtyCheck(entity) || !
> > > > entry.ExistsInDatabase || entry.LoadedState == null)
> > > >         {
> > > >             return false;
> > > >         }
> > > >         IEntityPersister persister = entry.Persister;
>
> > > >         object[] currentState = persister.GetPropertyValues(entity,
> > > > session.EntityMode); ;
> > > >         object[] loadedState = entry.LoadedState;
>
> > > >         return persister.EntityMetamodel.Properties
> > > >             .Where((property, i) => !
> > > > LazyPropertyInitializer.UnfetchedProperty.Equals(currentState[i]) &&
> > > > property.Type.IsDirty(loadedState[i], currentState[i], session))
> > > >             .Any();
> > > >     }
>
> > > > - When I call session.IsDirty(), it fires the SaveOrUpdateEvent
> > > > passing it the associated UserGroup, which shouldn't be changed;
>
> > > > If, however, I explicitly load the UserGroup instead of the User, when
> > > > I call session.IsDirty(), the SaveOrUpdateEvent is not fired, and the
> > > > session is not marked as dirty.
> > > > Any ideas? Is this a common/known problem?
>
> > > > <class name="User" lazy="false" table="`USER`">
> > > >     <id name="UsrId" access="property" column="`USR_ID`">
> > > >       <generator class="hilo" />
> > > >     </id>
> > > >     <property name="UsrEmail" type="String" column="`USR_EMAIL`"
> > > > length="100" />
> > > >     <property name="UsrEnabled" type="Boolean" column="`USR_ENABLED`" /
>
> > > >     <property name="UsrLogin" type="String" column="`USR_LOGIN`"
> > > > length="50" />
> > > >     <property name="UsrPassword" type="String" column="`USR_PASSWORD`"
> > > > length="50" />
> > > >     <property name="UsrRealName" type="String"
> > > > column="`USR_REAL_NAME`" length="100" />
> > > >     <set cascade="all" inverse="true" lazy="true" name="UserGroups">
> > > >       <key column="`USR_ID`" />
> > > >       <one-to-many class="UserGroup" />
> > > >     </set>
> > > >   </class>
>
> > > > <class name="UserGroup" lazy="false" table="`USER_GROUP`">
> > > >     <id name="UgrId" access="property" column="`UGR_ID`">
> > > >       <generator class="hilo" />
> > > >     </id>
> > > >     <many-to-one name="Profile" class="Profile" column="`PRF_ID`" not-
> > > > null="true" fetch="select" />
> > > >     <many-to-one name="User" class="User" column="`USR_ID`" not-
> > > > null="true" fetch="select" />
> > > >   </class>
>
> > > > I think the Profile mapping is irrelevant for this matter.
> > > > Thanks for your help, once again!
>
> > > > RP

-- 
You received this message because you are subscribed to the Google Groups 
"nhusers" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to 
[email protected].
For more options, visit this group at 
http://groups.google.com/group/nhusers?hl=en.

Reply via email to