So, you've integrated NHibernate as your ORM, you've created your objects and your mapping files, sooo... what next? The exciting part, that's what. I mean, I KNEW what an ORM was, what I didn't know is that my SQL would be taken care of for me, all LINQ-style in my code. What I didn't know was how manipulatable my objects would be with the functionality that NHibernate provide
IQuery: This is the most flexible, and frankly the least exciting, NHibernate data manipulation interface. It allows you to just run an inline query and return either a list, or a single object. To return a list you would just
IList listIDs = session.CreateSQLQuery("select id from Foo where name = '" + name +"'").ToList();
For a single item you would use .UniqueResult() instead of .ToList(). Something I know is possible but haven't used yet is the CreateMultiQuery method, which allows the return of multiple query results for different criteria. You can also use CreateQuery in a more direct way with your objects by just instantiating your object then passing it into CreateQuery() and using .Add to add parameters to your query. This is more direct, but I have not used it because of this beauty:
ICriteria: Ok, so listen to this, you just pass in the TYPE of the object you are looking for along with some criteria and it puts together the whole query for you. Like if I'm only trying to find Foos when Foo.Name is something like Steve and sort it by ID then I do this (notice the use of implicit local variables, 3.5 rulez!):
var foo = new Foo();
var baz = session.CreateCriteria(foo.GetType())
.Add(Restrictions.Like("Name", "%Steve%"))
.AddOrder(Order.Desc("id"))
.List();
How awesome is that? Restrictions is a member of Nhibernate.ICriterion and provides you with a way to add equations, or search for values to limit your result set. I used the ”like” constraint since it is so familiar to we SQL cats, but there are many more. It's that easy. You can also do simple inserts and updates using a simple session.Save() transaction which is super handy.
Now, before you play with any of this fun stuff you need to remember to do the following
-Build your SessionFactory (this I do here not in my helper class, this is stolen code from somewhere on the intarnetz, if someone can find it I will credit.
-Check for an existing Nhibernate ISession (NOT ASP.NET Session)
-Open a Nhibernate ISession (if one does not already exist)
-Then load your objects like above.
The funnest (I know, and I don't care) thing I have done so far is refactor the above behavior into a helper class. I am going to give it to you below because I love it and think it is great. Tell your friends, and have fun with Nhibernate (possibly also have fun with all the time you save, maybe earn some CrackOverflow points).
public class NHibernateObjectHelper
{
public static ISession session;
public static T LoadDataObject<T>(int Id)
{
session = CheckForExistingSession();
var returnObject = session.Get<T>(Id);
return returnObject;
}
public static IList<T> LoadObjectListAll<T>()
{
session = CheckForExistingSession();
var criteria = session.CreateCriteria(typeof(T));
var results = criteria.List<T>();
return results.ToArray();
}
public static ISession OpenDataObjectSession()
{
session = NHibernateSessionFactory.OpenSession();
return session;
}
public static ISession CheckForExistingSession()
{
if(session == null)
session = OpenDataObjectSession();
return session;
}
public static void CloseSession()
{
session.Close();
}
public static void Save(BaseObject<int> businessObject)
{
session = CheckForExistingSession();
var transaction = session.BeginTransaction();
session.Save(businessObject);
transaction.Commit();
}
public static void Update(BaseObject<int> businessObject)
{
session = CheckForExistingSession();
var transaction = session.BeginTransaction();
session.Update(businessObject);
transaction.Commit();
}
}