Giving Clarity to LINQ Queries by Extending Expressions

27
λ Giving Clarity to LINQ Queries by Extending Expressions

Transcript of Giving Clarity to LINQ Queries by Extending Expressions

λGiving Clarity to LINQ Queries

by Extending Expressions

Ed CharbeneauDeveloper Advocate, TelerikCode PaLOUsa Co-ChairmanAuthor: TDN & Simple-TalkPodcast: Eat Sleep Code the Official Telerik PodcastTwitter: @EdCharbeneau

Are

Do you use

expressions?

Common uses

Entity Framewo

rkLINQ HTML

Helpers

Expression<Func<TModel, TResult>>

@Html.LabelFor(obj => obj.Prop)

Expression<Func<TModel, bool>>

People.Where(p => p.Title == “Developer”)

Expressions in C#

• Representation of code as data• Meta-programming– Analyze, rewrite, and translate code at

runtime

Expression Factory

+

11

Add

constant constant

SimpleBinaryExpression

Homo-iconicity

Same syntax for executable code as data representation

Compile

Runtime Modification

ExpressionVisitor• used to traverse or rewrite

expression trees• Abstract class– Inherit and override

• .Visit(expression)– Recursively walks the tree– Returns an Expression

https://msdn.microsoft.com/en-us/library/bb882521(v=vs.90).aspx

Are

How is this

useful?

Pipeline

Pipes and filters

Filter

Rule

Rule

Data

Data

Data

Consumer

Results

Database Filter

Rule

Rule

dbContext.Where(rule).Where(rule)

Maintainability & Readability

Refactoring

What’s

going on

here?

Let’s start simple

What’s

going on

here?

Distinction

The tale of two extension methods

IEnumerable.Where(q => q.Value == true)Func (delegate)Func<T, bool>

IQueryable.Where(q => q.Value == true)Expression

Expression<Func<T, bool>

LINQ Where Chaining

Custom Filters

(Expression<Func<TSource, bool>> predicate)

ParameterMethod

.Where<TSource>

Extends type

IQueryable<TSource>

Return type

IQueryable<TSource>

Generic type

Extends type

IQueryable<MyType>

Return type

IQueryable<MyType>

Method

.CustomMethodName()

public static IQueryable<Post> ArePublished(this IQueryable<Post> posts){ return posts.Where(post => post.IsPublished);}

Readability?

Before After

What’s the intent

?

Now what?

What’s

the intent

?

Lambda as an Expression tree

post => post.PostedOn >= cutoffDate

>=

cutoffDatePostedOn

GreaterThanOrEqual

=>

post

Lambda

parameter

parameter constant

Body

Combine Like Expressions?

>=

=>

post

Body

==

=>

post

Body

AND / OR?

Combined Expressions

=>

post

Lambda

parameter

Body

>=

&&

==

Readability?

Before

After

New Requirements!

Now we must support multiple featured authors

Dynamic LINQ

query?

No problem, now we’re equipped for it!

Dynamic Queries

Try this without expressions.

AreQuestion

s?