-->
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.  [ 14 posts ] 
Author Message
 Post subject: DataGridView Exceptions
PostPosted: Wed May 17, 2006 5:05 pm 
Regular
Regular

Joined: Fri Jan 27, 2006 2:32 pm
Posts: 102
Location: California, USA
Info:
Using NHibernate from subversion, Revision #2058
This is a Winforms application.

I am using QBE (query by example) to provide a search box in my application. I take the IList returned by QBE and bind it to a DataGridView.

The DataGridView throws this exception for some rows, but not all rows in the IList:

Code:
System.Reflection.TargetInvocationException: Property accessor 'RoleID' on object 'ChemManager.BusinessObjects.Security.Role' threw the following exception:'Object does not match target type.' ---> System.Reflection.TargetException: Object does not match target type.


It is consistent in the rows that it "hates", but if the IList contains 4 rows, not all 4 rows have an error. And it seems that the first row always works fine without error.

If I create an ArrayList of my business objects by hand (never fetched from the database, so they are not NH proxy objects) and bind that to a DataGridView, everything works fine.

Any ideas???


Top
 Profile  
 
 Post subject:
PostPosted: Wed May 17, 2006 7:01 pm 
Regular
Regular

Joined: Fri Jul 29, 2005 9:46 am
Posts: 101
Hi!
I haven't had that problem... but I always wrap the result of my query in a generic List...
Perhaps I can help you, but I need to see you class, and you mappings... and a bigger piece of your stacktrace


Top
 Profile  
 
 Post subject:
PostPosted: Wed May 17, 2006 7:54 pm 
Regular
Regular

Joined: Fri Jan 27, 2006 2:32 pm
Posts: 102
Location: California, USA
luxspes wrote:
Hi!
I haven't had that problem... but I always wrap the result of my query in a generic List...
Perhaps I can help you, but I need to see you class, and you mappings... and a bigger piece of your stacktrace


The problem occurs with all of my mapped classes, so I use Permission since it is one of the simplest.

Code:

using System;
using ChemManager.Attributes;

namespace ChemManager.BusinessObjects.Security
{

    public class Permission : IChangeLog
    {

        private static readonly log4net.ILog log =
            log4net.LogManager.GetLogger(System.Reflection.
            MethodBase.GetCurrentMethod().DeclaringType);

        public Permission()
        { }

        public override string ToString()
        {
            return _permissionName;
        }

        public virtual event EventHandler PermissionIDChanged;
        public virtual event EventHandler PermissionNameChanged;
        public virtual event EventHandler DescriptionChanged;
        public virtual event EventHandler LongDescriptionChanged;

        private long? _permissionID = null;
        private string _permissionName = null;
        private string _description = null;
        private string _longDescription = null;

        private long? _nhVersion = null;
        public virtual long? NhVersion
        {
            get { return _nhVersion; }
            private set { _nhVersion = value; }
        }

        private DateTime? _created = null;
        public virtual DateTime? Created
        {
            get { return _created; }
            private set
            {
                if (_created == null)
                    _created = value;
            }
        }

        private User _createdBy = null;
        public virtual User CreatedBy
        {
            get { return _createdBy; }
            private set
            {
                if (_createdBy == null)
                    _createdBy = value;
            }
        }

        private DateTime? _lastUpdated = null;
        public virtual DateTime? LastUpdated
        {
            get { return _lastUpdated; }
            private set { _lastUpdated = value; }
        }

        private User _lastUpdatedBy = null;
        public virtual User LastUpdatedBy
        {
            get { return _lastUpdatedBy; }
            private set { _lastUpdatedBy = value; }
        }

        [KeyField()]
        [ListField(0)]
        public virtual long? PermissionID
        {
            get { return _permissionID; }
            private set
            {
                _permissionID = value;

                if (PermissionIDChanged != null)
                    PermissionIDChanged(this, new EventArgs());
            }
        }

        [SearchField(0)]
        [ListField(1)]
        [FieldDescription("Permission Name", "Name")]
        public virtual string PermissionName
        {
            get { return _permissionName; }
            set
            {
                if (_permissionName == null)
                {
                    _permissionName = value;

                    if (PermissionNameChanged != null)
                        PermissionNameChanged(this, new EventArgs());
                }
            }
        }

        public virtual string Description
        {
            get { return _description; }
            set
            {
                _description = value;

                if (DescriptionChanged != null)
                    DescriptionChanged(this, new EventArgs());
            }
        }

        public virtual string LongDescription
        {
            get { return _longDescription; }
            set
            {
                _longDescription = value;

                if (LongDescriptionChanged != null)
                    LongDescriptionChanged(this, new EventArgs());
            }
        }

    }

}


Top
 Profile  
 
 Post subject:
PostPosted: Wed May 17, 2006 7:55 pm 
Regular
Regular

Joined: Fri Jan 27, 2006 2:32 pm
Posts: 102
Location: California, USA
This is the mapping file for the Permission class.

Code:
<?xml version="1.0" encoding="utf-8" ?>
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.0">
  <class name="ChemManager.BusinessObjects.Security.Permission, ChemManager "
         table="fw_permission">

    <id name="PermissionID" column="permission_id" type="long">
      <generator class="sequence">
        <param name="sequence">fw_permission_seq</param>
      </generator>
    </id>

    <!-- Standard Columns -->

    <version name="NhVersion" column="nh_version" type="long" />
    <many-to-one name="CreatedBy" class="ChemManager.BusinessObjects.Security.User, ChemManager" column="created_by" />
    <property name="Created" column="created" type="DateTime" />
    <many-to-one name="LastUpdatedBy" class="ChemManager.BusinessObjects.Security.User, ChemManager" column="last_updated_by" />
    <property name="LastUpdated" column="last_updated" type="DateTime" />

    <!-- End Standard Columns -->

    <property name="PermissionName" column="permission_name" type="String" />
    <property name="Description" column="description" type="String" />
    <property name="LongDescription" column="long_description" type="String" />

  </class>
</hibernate-mapping>


Top
 Profile  
 
 Post subject:
PostPosted: Wed May 17, 2006 7:58 pm 
Regular
Regular

Joined: Fri Jan 27, 2006 2:32 pm
Posts: 102
Location: California, USA
This is the code that performs the QBE

Code:
        public static IList SearchByExample(object searchObject)
        {
            ICriteria c =
                Connection.Session.CreateCriteria(searchObject.GetType());
            NHibernate.Expression.Example e =
                NHibernate.Expression.Example.Create(searchObject);

            e.ExcludeZeroes();
            e.ExcludeNulls();
            e.IgnoreCase();
            e.EnableLike(NHibernate.Expression.MatchMode.Start);
            c.Add(e);

            IList result = c.List();

            return result;
        }


And this is the code that is calling the QBE

Code:
private IList _searchResults = null;
_searchResults = Data.Search.SearchByExample(_searchObject);
dgvResults.DataSource = _searchResults;


Top
 Profile  
 
 Post subject:
PostPosted: Wed May 17, 2006 8:07 pm 
Expert
Expert

Joined: Fri May 13, 2005 5:56 pm
Posts: 308
Location: Santa Barbara, California, USA
can you provide the mapping file for the ChemManager.BusinessObjects.Security.User class?


Top
 Profile  
 
 Post subject:
PostPosted: Wed May 17, 2006 8:43 pm 
Regular
Regular

Joined: Fri Jan 27, 2006 2:32 pm
Posts: 102
Location: California, USA
devonl wrote:
can you provide the mapping file for the ChemManager.BusinessObjects.Security.User class?


Here it is:

Code:
<?xml version="1.0" encoding="utf-8" ?>
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.0">
  <class name="ChemManager.BusinessObjects.Security.User, ChemManager"
         table="fw_user">

    <id name="UserID" column="user_id" type="long">
      <generator class="sequence">
        <param name="sequence">fw_user_seq</param>
      </generator>
    </id>

    <!-- Standard Columns -->

    <version name="NhVersion" column="nh_version" type="long" />
    <many-to-one name="CreatedBy" class="ChemManager.BusinessObjects.Security.User, ChemManager" column="created_by" />
    <property name="Created" column="created" type="DateTime" />
    <many-to-one name="LastUpdatedBy" class="ChemManager.BusinessObjects.Security.User, ChemManager" column="last_updated_by" />
    <property name="LastUpdated" column="last_updated" type="DateTime" />

    <!-- End Standard Columns -->

    <property name="UserName" column="user_name" type="String" />
    <property name="DisplayName" column="display_name" type="String" />
    <property name="ActiveDirectorySID" column="active_directory_sid" type="String" />
    <property name="PrimaryMachineName" column="primary_machine_name" type="String" />

    <list name="Roles" cascade="all" generic="true" table="fw_user_roles">
      <key column="user_id" />
      <index column="list_index" />
      <many-to-many class ="ChemManager.BusinessObjects.Security.Role, ChemManager" column="role_id" />
    </list>

    <list name="Impersonations" cascade="all" generic="true" table="fw_user_impersonations">
      <key column="user_id" />
      <index column="list_index" />
      <many-to-many class ="ChemManager.BusinessObjects.Security.User, ChemManager" column="impersonate_user_id" />
    </list>

  </class>
</hibernate-mapping>


Top
 Profile  
 
 Post subject:
PostPosted: Wed May 17, 2006 8:46 pm 
Regular
Regular

Joined: Fri Jan 27, 2006 2:32 pm
Posts: 102
Location: California, USA
luxspes wrote:
... and a bigger piece of your stacktrace


Here is the stack:

Code:
   at System.ComponentModel.ReflectPropertyDescriptor.GetValue(Object component)
   at System.Windows.Forms.DataGridView.DataGridViewDataConnection.GetValue(Int32 boundColumnIndex, Int32 columnIndex, Int32 rowIndex)


There is an inner exception:

Code:
   at System.Reflection.RuntimeMethodInfo.CheckConsistency(Object target)
   at System.Reflection.RuntimeMethodInfo.Invoke(Object obj, BindingFlags invokeAttr, Binder binder, Object[] parameters, CultureInfo culture, Boolean skipVisibilityChecks)
   at System.Reflection.RuntimeMethodInfo.Invoke(Object obj, BindingFlags invokeAttr, Binder binder, Object[] parameters, CultureInfo culture)
   at System.ComponentModel.ReflectPropertyDescriptor.GetValue(Object component)


Top
 Profile  
 
 Post subject:
PostPosted: Thu May 18, 2006 8:17 am 
Contributor
Contributor

Joined: Wed May 11, 2005 4:59 pm
Posts: 1766
Location: Prague, Czech Republic
Looks like proxies might be at fault here. If you can reproduce this error using a simple self-contained example, please submit a bug report.


Top
 Profile  
 
 Post subject:
PostPosted: Thu May 18, 2006 3:28 pm 
Regular
Regular

Joined: Fri Jan 27, 2006 2:32 pm
Posts: 102
Location: California, USA
sergey wrote:
Looks like proxies might be at fault here. If you can reproduce this error using a simple self-contained example, please submit a bug report.


I created a single form that performed a QBE search and binded the resulting IList to a DataGridView.

It worked! No errors. No exceptions.

After much tinkering and looking in all the wrong places, I came back to the IList that is returned by QBE. Something had to be wrong there.

It turns out that the objects returned in the IList are not all of the same type. The DataGridView expects all of the objects to be of the same exact type. Here is the type name of each row in my IList::

Code:
?_searchResults[0].GetType().FullName
"CProxyTypePermissionSecurity_INHibernateProxy1"

?_searchResults[1].GetType().FullName
"ChemManager.BusinessObjects.Security.Permission"

?_searchResults[2].GetType().FullName
"CProxyTypePermissionSecurity_INHibernateProxy1"


And yes, the row that is not a Proxy type, that row is throwing exceptions and does not display in the DataGrid.

So, now I have no idea what to do about any of this. I'm not sure why they are not all Proxy objects or they are not all "Permission" objects. What is the difference between a proxy object and my regular BusinessObjects? I thought Proxy had to do with lazy loading, which I'm not intentionally trying to do.

Saving and loading and all other areas of the application work fine.

Any thoughts?

--Brian


Top
 Profile  
 
 Post subject:
PostPosted: Thu May 18, 2006 3:56 pm 
Contributor
Contributor

Joined: Wed May 11, 2005 4:59 pm
Posts: 1766
Location: Prague, Czech Republic
Err, it would be more understandable if the row that is a proxy produced errors, the other way around is just weird. If you can, please create a simple project, stripped down as much as possible, and submit a bug report. I'll try to debug the error.


Top
 Profile  
 
 Post subject:
PostPosted: Thu May 18, 2006 4:10 pm 
Regular
Regular

Joined: Fri Jan 27, 2006 2:32 pm
Posts: 102
Location: California, USA
sergey wrote:
Err, it would be more understandable if the row that is a proxy produced errors, the other way around is just weird.


I read somewhere that the DataGrid looks at the type of the first row, and then expects all of the remaining rows to be the same type. (So, if the first row was my non-proxy Permission object, then the two proxy objects would throw errors.).

sergey wrote:
If you can, please create a simple project, stripped down as much as possible, and submit a bug report. I'll try to debug the error.


I will try. Thanks for looking at this.


Top
 Profile  
 
 Post subject:
PostPosted: Thu May 18, 2006 4:52 pm 
Regular
Regular

Joined: Fri Jan 27, 2006 2:32 pm
Posts: 102
Location: California, USA
I think I need to read more about Sessions.

I started to think about why couldn't I reproduce this problem except in my full blown application. Then I realized that my application was doing lots of work and queries against the database all on the same session.

I remember something saying sessions should be "short lived". So, I thought, well let's refresh the session and see what that does.

YES, IT DID FIX IT! Ugh! I need to read more documentation.

Sorry to trouble everyone....

--Brian


Top
 Profile  
 
 Post subject:
PostPosted: Fri May 19, 2006 6:03 pm 
Regular
Regular

Joined: Fri Jan 27, 2006 2:32 pm
Posts: 102
Location: California, USA
Refreshing the Session caused more problems that I can count!

So I ended up going back to another idea.

The root problem is that the types of objects returned by the IList from the QBE are of different types. They need to be all of the same type, ... either all proxy objects or all my objects.

So, I created a new search form class that uses generics. When the IList is returend, I recast all of the results to the type of the form.

Basically, I take the IList that is a mixture of proxy objects and my business class objects, and cast them all back to my business class type. Then, the DataGridView works fine.

This sounds like a hack, but it seems to be working.


Top
 Profile  
 
Display posts from previous:  Sort by  
Forum locked This topic is locked, you cannot edit posts or make further replies.  [ 14 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.