Fetching strategies

ALL THE EXAMPLES FROM THIS POST ARE EXTRACTED FROM THE FWKLIGHT DEMO. TO FIND OUT HOW TO GET STARTED WITH THE DEMO, READ THIS POST.

Fetching strategies represent a way to tell NHibernate what you want to load inside an aggregate (or list of aggregates) before you load it.

You should use a fetching strategy whenever you need to load an aggregate with entities in it (or lists of entities in it), or lists of aggregates in which every element has entities in it (or lists of entities in it).

IT IS YOUR RESPONSABILITY TO USE FETCHING STRATEGIES WHENEVER YOU NEED TO LOAD AGGREGATES AND THEIR SUBENTITIES, WHEN WORKING WITH FWKLIGHT.

This mechanism provided by FwkLight offers you a way to completely define everything you want to load inside the aggregate, so you should never need to manually load something related to an aggregate after you already loaded the aggregate (doing so would make your implementation more complicated, and lower the stability of the code).

You create fetching strategies by writing classes which implement the IFetchingStrategy<T> interface. The key to configuring a fetching strategy is the IMultiCriteriaFetcher<T> interface, which offers a fluent interface (IListMultiCriteriaFetcher) through which you can instruct NHibernate on how to generate the NHibernate multicriteria for loading the aggregate (aggregates). When executed, the multicriteria will run a batch select on the database and load everything very efficiently, in one roundtrip.

In this example, the fetching strategy instructs FwkLight to load the CustomerOrder with its OrderDetails:

public class CustomerOrder1Fetching: IFetchingStrategy<CustomerOrder1>
{
    public void ApplyStrategyOn(IMultiCriteriaFetcher<CustomerOrder1> repository)
    {
        repository
            .InitFetchingHierarchy()
            .WhichAlsoContainsList(p => p.OrderDetails);
    }
}

The query has the CustomerOrder1Fetching strategy specified, so each time the query is executed it will load its list of orders according to this strategy:

public class AggregateListQuery3 : MultiCriteriaQuery<CustomerOrder1>
{
    private readonly CustomerOrder1Fetching _customerOrder1Fetching;
    private decimal _minPrice;

    public AggregateListQuery3(CustomerOrder1Fetching customerOrder1Fetching)
    {
        _customerOrder1Fetching = customerOrder1Fetching;
    }

    public IList<CustomerOrder1> Execute(ISession session, decimal minPrice)
    {
        _minPrice = minPrice;
        return Load(session);
    }

    protected override void ApplyMainFilters(IListMultiCriteriaFetcher<CustomerOrder1> criteria)
    {
        criteria.Where(p => p.OrderPrice).Gt(_minPrice);
    }

    protected override IFetchingStrategy<CustomerOrder1> FetchingStrategy
    {
        get
        {
            return _customerOrder1Fetching;
        }
    }

    protected override void FilterOnlyActive(IListMultiCriteriaFetcher<CustomerOrder1> criteria) { }

    protected override void Sort(IListMultiCriteriaFetcher<CustomerOrder1> criteria) { }
}

Advertisement

About this entry