Archive for April, 2009

Load with filtering or limiting

Today, you have two direct options how to load related data for given entity. Use Include or use Load method. In this post, I’ll focus on Load, because this problem on Include is little bit easier than on Load. Unfortunately the Load method isn’t providing any option to filter or limit what you’re loading. That means, if you have customer with for example 200 invoices, you’ll load all these 200 invoice, even if you need only first 5 or something like that. And that’s wasting of resources.

But the solution isn’t so hard. First, Entity Framewok has automagic wiring of related entities. Hence if you load one customer and then some invoices. If there will be invoices for this customer the navigation properties will be working without problem and without any work form you. So the first solution for filtered load is simply load detail record with your where condition and condition on the master entity. But that’s “a lot” of work ;) and developers are lazy. Fortunately there’s another way.

The EntityReference has a method CreateSourceQuery returning ObjectQuery. With this and knowledge from previous paragraph you can easily create overload/extension method for Load to load only what you need.

public static void Load<T>(this EntityCollection<T> relatedEnd, Expression<Func<T, bool>> predicate, MergeOption mergeOption) where T : class, IEntityWithRelationships
{
	(relatedEnd.CreateSourceQuery().Where(predicate) as ObjectQuery<T>).Execute(mergeOption).ToArray();
}

public static void Load<T>(this EntityReference<T> relatedEnd, Expression<Func<T, bool>> predicate, MergeOption mergeOption) where T : class, IEntityWithRelationships
{
	(relatedEnd.CreateSourceQuery().Where(predicate) as ObjectQuery<T>).Execute(mergeOption).ToArray();
}

public static void Load<T>(this EntityCollection<T> relatedEnd, Expression<Func<T, bool>> predicate) where T : class, IEntityWithRelationships
{
	Load(relatedEnd, predicate, MergeOption.AppendOnly);
}

public static void Load<T>(this EntityReference<T> relatedEnd, Expression<Func<T, bool>> predicate) where T : class, IEntityWithRelationships
{
	Load(relatedEnd, predicate, MergeOption.AppendOnly);
}

Above is simple extension method, to help you load only related entities you need based on some where condition. You can take the same idea and create a version with First, for instance. Or any filter or limit you may need.

  • Twitter
  • Facebook
  • Share/Bookmark

Tags: ,

BuildNotContainsExpression

Colin Meek wrote extremely handy method for using it as Contains method we know it’s on collections, but not supported in Entity Framework right now (v1/EF3.5). The method is called BuildContainsExpression. Today in MSDN forums I needed this, but negated. Thus I wrote the BuildNotContainsExpression. It’s just small change of original Colin’s method.

static Expression<Func<TElement, bool>> BuildNotContainsExpression<TElement, TValue>(Expression<Func<TElement, TValue>> valueSelector, IEnumerable<TValue> values)
{
    if (null == valueSelector) { throw new ArgumentNullException("valueSelector"); }
    if (null == values) { throw new ArgumentNullException("values"); }

    ParameterExpression p = valueSelector.Parameters.Single();

    // p => valueSelector(p) != values[0] && valueSelector(p) != ...

    if (!values.Any())
    {
        return e => true;
    }

    var equals = values.Select(value => (Expression)Expression.NotEqual(valueSelector.Body, Expression.Constant(value, typeof(TValue))));
    var body = equals.Aggregate<Expression>((accumulate, equal) => Expression.And(accumulate, equal));
    return Expression.Lambda<Func<TElement, bool>>(body, p);
}
  • Twitter
  • Facebook
  • Share/Bookmark

Tags: ,

Instead of triggers in MS SQL and Entity Framework problem

I don’t like the model of instead of and after triggers in MS SQL. The before and after ones are, in my opinion, better. Anyway I needed to do some complex tests, not possible with check constraints, before inserting. Hence I jumped into instead of trigger. No problem in a view. Or not?

The Entity Framework is smart enough to get all server generated columns back when inserting (or updating) – see StoreGeneratedPattern. But the problem is how the identity column, often used for primary keys, is retrieved. The command issued after insert looks like (particular shape depends on other store generated columns and concurrency checks): select <PK column> from <some table> where @@ROWCOUNT > 0 and <PK column> = scope_identity().The problem is, that if you generate new PK value in trigger, it is different scope. Thus this command returns zero rows and EF will throw exception.

Hmm, this isn’t the way. :( So one of the solutions is move away from instead of triggers and use stored procedures (remember that you need all three) and result binding (you might be forced to create SPs (of fake ones in SSDL) for some related objects too). It’s not easiest solution, but works nice and you don’t have to introduce hacks etc.

  • Twitter
  • Facebook
  • Share/Bookmark

Tags: ,

Entity Framework and Firebird Embedded

Did you ever think about how cool would be to have fully featured SQL database, without installation (just xcopy) and with Entity Framework support?

I was wondering whether the Entity Framework support I’m creating in FirebirdClient will work with Embedded version. Taking into account that the communication layers are under the EF support, there should be no problem. But you’ll never be sure until you try it. ;) And it works.

So what you need to do? Well almost nothing. Just change connection string and it works. But maybe you’re starting with fresh app, thus I’ll give you some advices. To be able to generate proper model (at least the SSDL), you need 2.5 Beta 1 (released couple days ago) – it has the left outer join bug fixed. Also since 2.5 you’ll be able to connect to database using different applications, therefore debugging the application and using i.e. isql together is even easier. On the development machine you probably already have .NET Framework 3.5 with SP1, but also remember to have it on target machine. (Saying that you need FirebirdClient is I think worthless. ;) )

And that’s pretty much it. After you finish your app you can deploy it with i.e. 2.1 Embedded (it’s the current stable), the app will run just fine.

Isn’t it nice? Full power of proper database server and full power of Entity Framework all in one.

  • Twitter
  • Facebook
  • Share/Bookmark

Tags: ,

(Not) interesting observation on LINQ

I’ve found interesting stuff in last couple of … I don’t know. Well it’s not interesting because everybody knows it :) , but using it this way, was for me like going the other direction.

First is that code comprehension (which I don’t like, btw) is translated into well known methods like Select, Where etc. You are using this in LINQ often. But it’s not coupled to IQueryable or whatever, it’s just dumb translation during compile. Hence you can easily provide i.e. only Select and Where methods in your class and use it with code comprehension. Not worrying about IQueryable or runtime exceptions if don’t support some methods. Obvious, right? I told you. :)

Another observation is that your i.e. Where method may return completely different class or collection of classes. This is probably not usefull at all, although as a mind blowing code to torture your colleagues it can be fun. ;)

  • Twitter
  • Facebook
  • Share/Bookmark

Tags:

Sorting in IQueryable using string as column name

Today my UI/ASP.NET guru workmate asked me whether it’s possible to provide sorting methods on queries (in our case Entity Framework) using column name as string instead of expression. Well, I thought, why it shouldn’t.

My first attention got to the MetadataWorkspace. After couple of attempts it became clear that this is not the best way. So I switched my attention to the expression trees. And that was the way. I ended up with this result.

private static IOrderedQueryable<T> OrderingHelper<T>(IQueryable<T> source, string propertyName, bool descending, bool anotherLevel)
{
    ParameterExpression param = Expression.Parameter(typeof(T), string.Empty); // I don't care about some naming
    MemberExpression property = Expression.PropertyOrField(param, propertyName);
    LambdaExpression sort = Expression.Lambda(property, param);

    MethodCallExpression call = Expression.Call(
        typeof(Queryable),
        (!anotherLevel ? "OrderBy" : "ThenBy") + (descending ? "Descending" : string.Empty),
        new[] { typeof(T), property.Type },
        source.Expression,
        Expression.Quote(sort));

    return (IOrderedQueryable<T>)source.Provider.CreateQuery<T>(call);
}

public static IOrderedQueryable<T> OrderBy<T>(this IQueryable<T> source, string propertyName)
{
    return OrderingHelper(source, propertyName, false, false);
}

public static IOrderedQueryable<T> OrderByDescending<T>(this IQueryable<T> source, string propertyName)
{
    return OrderingHelper(source, propertyName, true, false);
}

public static IOrderedQueryable<T> ThenBy<T>(this IOrderedQueryable<T> source, string propertyName)
{
    return OrderingHelper(source, propertyName, false, true);
}

public static IOrderedQueryable<T> ThenByDescending<T>(this IOrderedQueryable<T> source, string propertyName)
{
    return OrderingHelper(source, propertyName, true, true);
}

It’s a set of extension methods with similar signature as the classic ones OrderBy, ThenBy, etc. only taking string parameter instead of expression. This string parameter is name of field in class to be used for sorting. Enjoy.

  • Twitter
  • Facebook
  • Share/Bookmark

Tags: ,

Zajímavá fičurka pro nastavení zvuku

Při dnešním čtení TechNet magazínu (Windows Confidential: Finding the Right Volume) jsem narazil na zajímavou feature ve Vistě aspol. Jmenuje se Loudness Equalization [Control Panel > Sound > Playback > Properties > Enhancements] (nemám český systém, takže nevím jak tam) a v podstatě dělá to, že jednou nastavíte hlasitost, která vám vyhovuje a systém pak hlasitost veškerých zvuků, které půjdou ven upraví na tuto úroveň. Takže se nadále o hlasitost nemusíte starat.

Určitě tomu zkusím dát šanci, mohlo by to vyřešit neustálé nastavování hlasitosti podle toho co zrovna člověk přehrává. Ačkoli mám obavy, že vzhledem k tomu, že používam někdy notebook i bez sluchátek, bude třeba někdy korekce na novou hlasitost a pak zpět.

  • Twitter
  • Facebook
  • Share/Bookmark

Tags:

Eager loading cost – another stuff to consider

Julie Lerman made a great post about The cost of eager loading in Entity Framework. And everything there is true, in fact if you take my Entity Framework training, you will know that with all reasons and you’ll also learn performace improvements you may incorporate into your solution.

I want to make some small addition to this post. There’s another stuff to think about. That’s the cost of processing query on server.

You should always consider the cost of parsing, compiling, finding execution plan etc. the query on server as well as fetching the intermediate data (which may cause cleaning up caches etc.). Thus sometimes (and we’re back to balance as Julie said) it’s better to issue couple of smaller (not so complex) queries, rather than one huge query.

  • Twitter
  • Facebook
  • Share/Bookmark

Tags: ,

FirebirdClient 2.5.0 Beta 2

I’m glad to announce Beta 2 release of FirebirdClient 2.5.0.

This release contains implementation of new Firebird 2.1 protocol,
couple of bugfixes in Entity Framework support and other bug fixes and
improvements.

Thanks SMS-Timing for support on new protocol and Entity Framework support and Vlad Khorsun for answering all my questions on new protocol.

Download on http://www.firebirdsql.org/index.php?op=files&id=netprovider.

For more information about this release visit:
http://tracker.firebirdsql.org/secure/ReleaseNote.jspa?version=10340&styleName=Text&projectId=10003
for detailed changes follow the SVN log or visit:
http://tracker.firebirdsql.org/browse/DNET?report=com.atlassian.jira.plugin.ext.subversion:subversion-project-tab

  • Twitter
  • Facebook
  • Share/Bookmark

Tags: , , , , ,

Zooming in Entity Data Model Designer – pain for source control

From the beginning, when we discovered, that the EDMX file contains also section for design time stuff we knew, that it’s not the best for source control systems (i.e. Subversion). Yesterday I found another nasty feature. Even if you’re not moving entities in designer, changing zoom is also saved into the file. Can the collision making be easier?

Couldn’t help but wonder, why is zoom number saved? Maybe then the scroll position could be saved too. :)

I hope in next versions of VS the designer stuff and model itself will be split. Or you can use EdmGen2 and commit only CSDL, MSL, SSDL files and use EDMX just for changing stuff in VS.

  • Twitter
  • Facebook
  • Share/Bookmark

Tags: