Search code examples
entity-framework-4includepocoentity-relationshipmulti-step

EF4 Getting Associations In Separate Queries When Using POCOs


I want to build up an object graph using Entity Framework 4.2.

Right now, I have POCO entities, using ICollection for navigation properties. I want to avoid using EntityCollection or anything EF-specific.

I want to avoid massive joins caused by using Include excessively. Given an object, I want to populate its navigation properties, resulting in a separate database query.

Is there a way to populate an ICollection directly? Right now, I am working around the problem, but it is really painful.

// grab the user, brand users and brands
User user = entities.Users
                    .Include(item => item.BrandUsers.Select(brandUser => brandUser.Brand))
                    .Where(item => item.Name == userName)
                    .SingleOrDefault();
// grab the pending share grants and brands
entities.Users
        .Include(item => item.ToShareGrants.Select(shareGrant => shareGrant.Brand))
        .Where(item => item.Id == user.Id)
        .Load();
return user;

One thing I don't like about this approach is that I am re-querying the top-level object. If I don't do this, the navigation property isn't populated (left NULL) when there are no objects returned. For instance, the following code only works if results are returned:

entities.ShareGrants
        .Include(item => item.Brand)
        .Where(item => item.ToUserId == user.Id)
        .Load();

I was curious if there was just a method I wasn't aware of in entity framework for building these types of relationships. If anyone knows an easy approach to filling out navigation properties in steps, I'd appreciate a code sample.


Solution

  • The short answer to this question is that EF4 did not directly support the functionality I wanted. In order to prevent a massive join and break the results out across multiple calls to the database, the top-most entity must be downloaded from the database again. This means the left-most columns in the result set will be the columns of that entity repeated for each record.