NHibernate and Future Queries, Part 2

1 Comment »Written on January 26th, 2009 by
Categories: NHibernate

In my last post i showed you how we can now use the Future feature in NHibernate. The only downside to the feature is that we only have the Future method in ICriteria, which returns a generic IEnumerable. Which doesn't really lead to nice code when dealing with queries that return a scalar value, or just a single row in general. So i decided to extend the feature a little bit.

I introduced the IFutureValue interface, which only defines a Value property:

    public interface IFutureValue<T>
    {
        T Value { get; }
    }

Then i added the FutureValue method on ICriteria, which returns an IFutureValue instance which behaves exactly like the IEnumerable that is returned by the Future method. If you access the Value property of the IFutureValue instance, it will either execute all of the currently queued Future queries in a single roundtrip, or it will simply return the result if the queries were already executed.

Here's some useless sample code to show off the feature:

            using (ISession session = sessionFactory.OpenSession())
            {
                IFutureValue<int> categoryCount = session.CreateCriteria(typeof(ProductCategory))
                    .SetProjection(Projections.RowCount())
                    .FutureValue<int>();
 
                IFutureValue<Supplier> mySupplier = session.CreateCriteria(typeof(Supplier))
                    .Add(Restrictions.Eq("Id", supplierId))
                    .FutureValue<Supplier>();
 
                IEnumerable<Product> allProducts = session.CreateCriteria(typeof(Product))
                    .Future<Product>();
 
                // the next line causes the 3 queries to be executed
                int count = categoryCount.Value;
                Supplier retrievedSupplier = mySupplier.Value;
 
                foreach (var product in allProducts)
                {
                    // yada yada yada... we're doing something important
                }

This is available starting with revision 4000, or in the official NHibernate 2.1 release.