Alessandro Del Sole's Blog

/* A programming space about Microsoft® .NET® */
posts - 159, comments - 0, trackbacks - 0

My Links

News

Your host

This is me! This space is about Microsoft® .NET® and Microsoft® Visual Basic development. Enjoy! :-)

These postings are provided 'AS IS' for entertainment purposes only with absolutely no warranty expressed or implied and confer no rights.

Microsoft MVP

My MVP Profile

I'm a VB!

Watch my interview in Seattle

My new book on VB 2015!

Pre-order VB 2015 Unleashed Pre-order my new book "Visual Basic 2015 Unleashed". Click for more info!

My new book on LightSwitch!

Visual Studio LightSwitch Unleashed My book "Visual Studio LightSwitch Unleashed" is available. Click the cover!

Your visits

Follow me on Twitter!

CodePlex download Download my open-source projects from CodePlex!

Article Categories

Archives

Post Categories

.NET Framework

Blogroll

Help Authoring

Microsoft & MSDN

Setup & Deployment

Visual Basic 2005/2008/2010

Strongly typed eager loading in Entity Framework with Visual Basic

In a previous post we discussed about creating data forms for showing master-details data representations with Visual Basic 2008 and the ADO.NET Entity Framework and we said that using strings within the eager loading technique could cause the loss of the benefits provided by the LINQ strongly typed approach.

 

I then found a blog post by Matthieu Mezil (Microsoft Visual C# MVP), who solved the problem implementing a custom Include method using lambda expressions instead of strings, taking the advantage of the strongly typed approach. Matthieu's code is in Visual C# with his help we converted the code into Visual Basic 2008.

 

The code is quite short, but it requires a good knowledge of LINQ, so you'll find links to the MSDN library for each object we will utilize.

 

Let's retake the demo application we saw in the previous post then let's add a new module. In this module we must first add the following Imports directives:

 

Imports System.Runtime.CompilerServices

Imports System.Data.Objects

Imports System.Linq.Expressions

Imports System.Reflection

 

Once we've done this, let's type the following code which implements an extension version of the Include method. This is the code about the new module and that we'll comment below:

 

<Extension()> Module ObjectQueryExtension

 

    <Extension()> _

    Function Include(Of T)(ByVal MainQuery As ObjectQuery(Of T), _

                           ByVal SubSelector As Expression(Of Func(Of T, Object))) _

                           As ObjectQuery(Of T)

 

        Return MainQuery.Include(CType(CType(CType(SubSelector.Body,  _

                                 UnaryExpression).Operand,  _

                                 MemberExpression).Member,  _

                                 PropertyInfo).Name)

    End Function

End Module

 

Extension methods must be adorned with the Extension attribute and must be exposed by modules adorned with the same attribute. The Include method requires a generic type Of T. The first argument the method receives is of type ObjectQuery(Of T), that represents, in a strongly typed way, a query executed versus the Entity Data Model. In our case the ObjectQuery is constituted by the NorthwindContext.Categories object. The secund argument is of type Expression (Of TDelegate), and is a strongly typed representation of a lambda expression that is structured as an expression tree.

The method body invokes the Include method versus the ObjectQuery instance that it received (in our sample it's always the NorthwindContext.Categories).

The lambda expression body is converted into an UnaryExpression. The result of this expression (Operand) is then converted into a MemberExpression, which is the infrastructure for accessing fields or properties which are then accessed via the reflection.

 

Invoking this method is quite easy. If we would apply the method to the demo application we saw in the previous post, we can replace the line of code for the eager loading as follows: 

 

        'Dim dataSource = NorthwindContext.Categories.Include("Products")

 

        Dim dataSource = NorthwindContext.Categories.Include(Function(c) c.Products)

 

You can surely notice the difference. We are no more passing a string, because we are now passing a lambda expression that allows us working in a strongly typed way (with many advantages from this). The local type inference correctly assigns the Categories type to the c object and the ObjectQuery(Of Categories) type to the dataSource one.

 

If you try to run the application you'll obtain the same result of the previous time, but this time we retrieved data with a more efficient and "managed" approach.

 

Alessandro

Print | posted on martedì 20 gennaio 2009 00:59 | Filed Under [ Visual Basic LINQ/EF/OData ]

Feedback

No comments posted yet.

Post Comment

Title  
Name  
Email
Url
Comment   
Please add 5 and 7 and type the answer here:

Powered by:
Powered By Subtext Powered By ASP.NET