Thursday, November 15, 2007

NHibernate Screencast - Persisting the Address Book

A few weeks ago, Evan Hoff posted a screencast on building up a domain model in a test-first manner.   We talked about it and thought it might be interesting to show how to apply persistence to this already functioning and tested domain model.

So take a look and tell me what you think!  It weighs in at 40 minutes (I tried to keep it under 30 but hey).

Thursday, November 15, 2007 1:23:32 PM (Central Standard Time, UTC-06:00)
Hey Ben, you are the man !!
that was a pretty cool screencast, i've been learning NHibernate at work because of a this new project and my boss can't wait until .NET 3.5, anyway I didn't know that NHibernate would actually crated the DDL for your objects, that is way cool.

Yesterday i was trying to setup a few scenarios and manage to make NHiberanmte Insert,update, and delete and POCO (Person class) to the DB which directly maps to a ONE table "Person" table so that was pretty simple

The problem tha I also had another POCO that Derives from Person which is "Staff" so basically the "Staff" Class has a few extra properties along with the properties for "person" class: example:

Person(Firstname, LastName)
Staff(Email, Title) and also the properties from Person since Staff inherits from Person.

I wanted to Create 2 tables in the DB one called Person and one called Staff, and basically the "staffId" would be the same of a Person Id if there was a staff to be in the DB (does that makes sense)?

So to select A staff, there needs to be a Select Statement from person table and staff table that joins on personid = staffid, same is true for updates/deletes/selects

How can i Map The "Staff" POCO which inherits from Person, and Map that to tell NHibernate to use 2 Tables the "person" and "staff" table for Inserting, updating and deleting a "Staff" POCO ??????? HOw can i do that in NHibernamte?????????

Please tell me is pretty simple to do? right?

What about a Class that needs to be mapped to 3 tables? Like "SalarayEmployee" which inherits from "Staff" which inherits from "Person"

AM I Crazy or what?
Thursday, November 15, 2007 2:27:33 PM (Central Standard Time, UTC-06:00)
No you're not crazy :)

That's a common scenario. You have inheritance in your code, but not in the database.

You have a few options. You could completely isolate the tables (which means you'd have duplicate columns). This is called table per concrete class. I don't like this approach, but it's possible.


you could also have 1 shared base table for the base class, and rely on a shared primary key with the common columns in the base table.

So something like this:

table user
user_id
first_name
last_name

table employee
user _id (same as above)
salary


This models the inheritance relationship nicely, but the problem is that now we have to do a join to get an employee, which is always slower than a single table select. This is called Table Per Subclass.

To get around that you can choose to flatten your hierarchy and just have 1 massive table, but a lot of the unrelated columns will be null. you also need a "Discriminator" column to tell NH what type of record each one is. This is called Table Per Hierarchy.

Do a google search on those 3 terms and you'll see what I mean.
Thursday, November 15, 2007 9:31:14 PM (Central Standard Time, UTC-06:00)
I think i found my solution here: http://www.hibernate.org/hib_docs/nhibernate/html/inheritance.html
I'll let you know if it works the way I wanted :) i agree with you joining is slower but is nice to know that is there so that we i design the DB i'll know the design can work too
Thursday, November 15, 2007 10:06:26 PM (Central Standard Time, UTC-06:00)
Thanks for this Ben. I wasnt aware that it was so easy to generate the schema.

Just out of curiousity (I know this was demo code), but isn't it kind of overkill to test the nHibernate functionality? Checking the mapping files as a sanity check seems ok, but don't you have to draw the line somewhere? Just like I wouldn't run unit tests against System.Math.Max, at some point don't you need to have a little faith in the framework?
Thursday, November 15, 2007 11:04:25 PM (Central Standard Time, UTC-06:00)
You bring up an interesting point.

I'm really not testing NHibernate here, I'm testing that I've mapped all of my properties, my primary keys and (eventually) my relationships with other entities.

I usually start out this low level and then I progress into more service/repository level testing. Hopefully I can demonstrate that in a future screencast.
Friday, November 16, 2007 4:59:13 PM (Central Standard Time, UTC-06:00)
I have a suggestion to make it to create a screen cast to demo the scenarios and more important the xml mappings for the diferent ways to map entities to teh database

such as

table per class hierarchy

table per subclass

table per concrete class
Monday, November 19, 2007 8:34:31 AM (Central Standard Time, UTC-06:00)
Great work !

please, make codes available for downloading :)

Bye !
Thursday, November 29, 2007 4:07:01 PM (Central Standard Time, UTC-06:00)
I enjoyed the screencast - I've just been getting into TDD and I had used Evan's screencast as one of my starting points. I appreciate getting to see how different people work as well as how different tools (like nHibernate) are used.

Thanks and I look forward to more!
Friday, January 11, 2008 5:52:20 AM (Central Standard Time, UTC-06:00)
Good Screencast.

I am looking for more resources on how to build an nhibernate helper class that creates the sessions and manages the nhibernate configuration for the application. Also on how to add a second level cache using this class. Any pointers on where to look?
Comments are closed.
Remortgage - Loans - Credit Card Consolidation - Credit Counseling