Thursday, March 19, 2009

nHibernates poor validation of mapping files

One thing that I have come to notice as I've been using nHibernate is that it does a very poor job at validating that mapping files make sense. One could argue that I shouldn't write poor shoddy mapping files in the first place. I would beg instead to tell me when I've written a poor shoddy mapping file.

Here's the scenario I just faced. I was working with an Entity which has a One to One relationship with some legacy code which doesn't use nHibernate. When I first mapped this I had an identity column on the table. After thinking about it, I want to enforce that we have a one to one so I then modified my schema and mapping file to use the FK field as its identity. I went from this:



class name="MyOptions"  lazy="false">


    <id column="id" name="Id"  >


        <generator class="native"/>


    </id>


    <property name="FkId"/>


</class>





To this:



<class name="MyOptions"  lazy="false">


    <id column="FkId" name="FkId" unsaved-value="any">


        <generator class="assigned"/>


    </id>


    <property name="FkId"/>


</class>




I fire this up, and we have no initialization issues, I am also to read data in without an issue. But when I go to save the data, I get an IndexOutOfRange exception when nHibernate tries to access a parameter.

Do you see the issue? I left my property for FkId in the mapping file. I needed to remove it since it is now the Id. Which caused parts of nHibernate to break. Interestingly enough when I look at the insert statement it only had the FkId field being inserted into once. So part of nHibernate handles my shoddy mapping file but other parts do not.

Anyways nHibernate is still an awsome tool, and hats off to the people who devote their time without pay to such a great tool.

3 comments:

Nitin R.K. said...

I love the LLBLGen ORM. It's more of a code generator but it's pretty amazing! It can deal with multiple databases, calling stored procedures is as simple as a method call, and it has a LINQ provider that they claim generates better SQL than LINQ2SQL or LINQ2EF.

Josh Berke said...

I'll add it to my list of things to check out. I am very happy with nHibernate, and code generators leave a really sour taste in my mouth.

Nitin R.K. said...

Hi Josh!

I know what you mean - I felt the same way about code generators till I used LLBLGen.

Unlike other code generators, LLBLGen tries to preserve the code that it already generated - if you rename a database field, the ORM will keep the property name in .NET unchanged so you don't have to refactor your code. Finding property names in .NET code might be simple with the Refactor tool, but it would miss data bindings in ASP.NET code.

-Nitin