-->
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.  [ 3 posts ] 
Author Message
 Post subject: Problem With Nullable Enumerations
PostPosted: Mon Jul 02, 2007 6:49 pm 
Newbie

Joined: Thu Jun 28, 2007 7:30 pm
Posts: 7
When I try to query a property that is a nullable enumeration (Nullable<ItemStatus>) via ICriteria I get a FormatException (nested inside an ADOException).

Neither the Linq version nor the ICreteria version work. Oddly enough, if I use dynamic linq (should be included in the orcas beta) it works just fine.


Hibernate version:

NHibernate 1.2.0.4000

Mapping documents:
Code:
<?xml version="1.0" encoding="utf-8" ?>
<hibernate-mapping xmlns="urn:nhibernate-mapping-2.2" assembly="PFE.Core" namespace="PFE">
   <class name="Item" table="Items">
      <id name="DBID" column="ID">
         <generator class="guid" />
      </id>
      <property name="ItemID" />
      <property name="Sku" />
      <property name="Title"  />
      <property name="Quantity" />
      <property name="QuantityAvailable" />
      <property name="BidCount" />
      <property name="StartPrice" />
      <property name="BuyItNowPrice" />
      <property name="ReservePrice" />
      <property name="ConvertedCurrentPrice" />
      <property name="ListingFee" />
      <property name="HasThumbnail" />
      <property name="HighBidderUserID" />
      <property name="SiteID" />
      <property name="Duration" />
      <property name="EndTime" />
      <property name="StartTime" />
      <property name="ScheduleTime" />
      <property name="ListingType" />
      <property name="PrimaryCategory" />
      <property name="SecondaryCategory" />
      <property name="Status" column="status" />
      <property name="Duration" />
      <property name="Source" />
      <many-to-one column="UserAccountDBID" name="UserAccount" />
      <many-to-one column="ClassTemplateDBID" name="ClassTemplate" />
      <bag name="Transactions" table="Transactions" inverse="true">
         <key column="BuyerDBID" />
         <one-to-many class="Transaction"/>
      </bag>
   </class>
</hibernate-mapping>

Code between sessionFactory.openSession() and session.close():
Code:
         using (ISessionFactory nhibernate = nconfig.BuildSessionFactory())
         {
            using (NHibernate.ISession session = nhibernate.OpenSession())
            {
               Console.WriteLine("Session Initialized.");
               Console.WriteLine("{0} items waiting to be listed.", session.Linq<Item>().Where("Status == @0", ItemStatus.PendingAdd).Count())
               Console.WriteLine("{0} items waiting to be listed.", session.CreateCriteria(typeof(Item)).Add(new EqExpression("Status", ItemStatus.PendingAdd)).List().Count);
               Console.WriteLine("{0} items waiting to be listed.", session.Linq<Item>().Where(x => x.Status == ItemStatus.PendingAdd).Count());
            }
   }


Full stack trace of any exception that occurs:

at System.Number.StringToNumber(String str, NumberStyles options, NumberBuffer& number, NumberFormatInfo info, Boolean parseDecimal)
at System.Number.ParseInt32(String s, NumberStyles style, NumberFormatInfo info)
at System.String.System.IConvertible.ToInt32(IFormatProvider provider)
at System.Convert.ToInt32(Object value)
at NHibernate.Type.PersistentEnumType.GetValue(Object code)
at NHibernate.Type.PersistentEnumType.GetInstance(Object code)
at NHibernate.Type.PersistentEnumType.Get(IDataReader rs, Int32 index)
at NHibernate.Type.NullableType.NullSafeGet(IDataReader rs, String name)
at NHibernate.Type.NullableType.NullSafeGet(IDataReader rs, String[] names, ISessionImplementor session, Object owner)
at NHibernate.Type.AbstractType.Hydrate(IDataReader rs, String[] names, ISessionImplementor session, Object owner)
at NHibernate.Loader.Loader.Hydrate(IDataReader rs, Object id, Object obj, ILoadable persister, ISessionImplementor session, String[][] suffixedPropertyColumns)
at NHibernate.Loader.Loader.LoadFromResultSet(IDataReader rs, Int32 i, Object obj, Type instanceClass, EntityKey key, LockMode lockMode, ILoadable rootPersister, ISessionImplementor session)
at NHibernate.Loader.Loader.InstanceNotYetLoaded(IDataReader dr, Int32 i, ILoadable persister, EntityKey key, LockMode lockMode, EntityKey optionalObjectKey, Object optionalObject, IList hydratedObjects, ISessionImplementor session)
at NHibernate.Loader.Loader.GetRow(IDataReader rs, ILoadable[] persisters, EntityKey[] keys, Object optionalObject, EntityKey optionalObjectKey, LockMode[] lockModes, IList hydratedObjects, ISessionImplementor session)
at NHibernate.Loader.Loader.GetRowFromResultSet(IDataReader resultSet, ISessionImplementor session, QueryParameters queryParameters, LockMode[] lockModeArray, EntityKey optionalObjectKey, IList hydratedObjects, EntityKey[] keys, Boolean returnProxies)
at NHibernate.Loader.Loader.DoQuery(ISessionImplementor session, QueryParameters queryParameters, Boolean returnProxies)
at NHibernate.Loader.Loader.DoQueryAndInitializeNonLazyCollections(ISessionImplementor session, QueryParameters queryParameters, Boolean returnProxies)
at NHibernate.Loader.Loader.DoList(ISessionImplementor session, QueryParameters queryParameters)

Name and version of the database you are using:

Sql Server 2K5

The generated SQL (show_sql=true):

[ SELECT this_.ID as ID6_0_, this_.ItemID as ItemID6_0_, this_.Sku as Sku6_0_, this_.Title as Title6_0_, this_.Quantity as Quantity6_0_, this_.QuantityAvailable as Quantity6_6_0_, this_.BidCount as BidCount6_0_, this_.StartPrice as StartPrice6_0_, this_.BuyItNowPrice as BuyItNow9_6_0_, this_.ReservePrice as Reserve10_6_0_, this_.ConvertedCurrentPrice as Convert11_6_0_, this_.ListingFee as ListingFee6_0_, this_.HasThumbnail as HasThum13_6_0_, this_.HighBidderUserID as HighBid14_6_0_, this_.SiteID as SiteID6_0_, this_.Duration as Duration6_0_, this_.EndTime as EndTime6_0_, this_.StartTime as StartTime6_0_, this_.ScheduleTime as Schedul19_6_0_, this_.ListingType as Listing20_6_0_, this_.PrimaryCategory as Primary21_6_0_, this_.SecondaryCategory as Seconda22_6_0_, this_.status as status6_0_, this_.Source as Source6_0_, this_.UserAccountDBID as UserAcc25_6_0_, this_.ClassTemplateDBID as ClassTe26_6_0_ FROM Items this_ WHERE this_.UserAccountDBID = 'd6323ba8-7dc4-49f2-8637-475059fa467f' AND this_.status = ? ]

Positional parameters: 0 PendingAdd

Debug level Hibernate log excerpt:

I can't get log4net to work right, but if someone can point me to a detailed guide on how I will.


Top
 Profile  
 
 Post subject:
PostPosted: Tue Jul 03, 2007 1:59 am 
Contributor
Contributor

Joined: Wed May 11, 2005 4:59 pm
Posts: 1766
Location: Prague, Czech Republic
The detailed guide for log4net is at http://www.hibernate.org/Documentation/ConfiguringLog4netForUseWithNHibernate.

In your case I'd like to know what the actual value in the column is - apparently it's not NULL (DBNull.Value), or NHibernate would have returned null correctly.


Top
 Profile  
 
 Post subject:
PostPosted: Tue Jul 03, 2007 12:42 pm 
Newbie

Joined: Thu Jun 28, 2007 7:30 pm
Posts: 7
Thanks for helping me setup log4net.

It turns out the problem is not with the Status property, it's with SiteID / ListingType properties. They are nullable enums stored as strings in the database, and nhibernate is assuming they are numbers.

Here is how I fixed it:
Code:
public class EnumAsString<T> : EnumStringType
{
   public EnumAsString()
      : base(typeof(T))
   {
   }
}


Apparently even if your POCO's property is nullable, you don't have to say so in your IUserType / xml definition.
Code:
<property name="EnumValue" type="EnumAsString`1[[MyEnum, MyAssembly]]" />


There, works like a charm!


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