A big step for Stored Procedures in EF4

When you are building or updating a model from a database, included Stored Procedures find their way into the SSDL (Store Schema Description Layer) of the metadata but not into the conceptual model. In order to expose them in your model, you need to create something called a Function Import which imports that stored proc from your SSDL into your model.

In EF4, when you run the Function Import Wizard, you will see a new option: Complex.

ef4sprocsb

Complex Types have been around since the beginning of Entity Framework however there was no designer support for them. Check this blog post (Complex Types in the EDM Designer in EF4 and a look at updating complex types in code) to see how the designer now supports Complex Types in VS2010.

The typical use of a complex type is as a property of an entity type. Here’s a Customer entity type which contains the complex type, Name. Name has 5 properties, FirstName, LastName, etc.

ef4sprocsa

Yet the Function Import wizard is not aimed at mapping part of the customer property.

A complex type is a class that can be instantiated. Even if it’s not a property of another type.

What this all boils down to is that you can receive the results of a stored procedure, whatever its shape, in the form of a complex type.

In EF version 1, there is no way to do this. You can return a scalar or an entity but nothing else. If you wanted to use a stored proc that returned something else, you would either have to create an entity plus a “fake” SSDL store representation and a mapping; all of this work was manual in the XML and a big PIA. If this was a drag for one stored proc, imagine if you had a lot of stored procedures. This problem became a show stopper for many development teams. Another way around the problem was to use Views rather than stored procs. (Check this blog post about that pattern:Entity Framework and Read Stored Procedures - a new perspective)

Now we have an option – though I’m hoping to see this fleshed out some more in Beta 2. Please, oh please!

Here’s a stored proc that returns data with a random shape – not matching any of the entities in my model.

CREATE PROCEDURE dbo.GetNames
AS
SELECT        CustomerID AS ID, RTRIM(LastName) +  ', ' + FirstName AS Name
FROM          SalesLT.Customer

In the Model Browser, I can define a complex type, such as CustName below, that matches the schema of my stored procedure result

ef4sprocsc

What’s really nice here compared to EFv1 is that I don’t need to create any other metadata to use this complex type.

Now I can map the stored procedure to that Complex Type using a Function Import.

ef4sprocsd

As I showed in my recent post, Checking out one of the new stored procedure features in EF4, import functions that did not return entities in EFv1 were hard to work with. If they returned a Scalar you could only use EntityClient to access the function. Now with functions that return a Scalar or a Complex Type, the default code generator creates the function directly in the generated ObjectContext.

       public ObjectResult<CustName> GetNames()
        {
            return base.ExecuteFunction<CustName>("GetNames");
        }

That means I can very easily call this function now.

This code declares a List of my Complex Type, CustName, calls the new GetNames function and converts the resulting ObjectResult<CustName) to a List.

     List<CustName> custs = context.GetNames().ToList();

This is a huge improvement, since I can now actually use existing stored procs that don’t line up with an entity. My hope (which I certainly raised with the EF Team is that if we have a lot of stored procs, we won’t have to do the manual steps of creating the complex type and the running the Function Import Wizard for each one.

Shout it
#1 onemenny on 8.02.2009 at 2:48 AM

This is gr8t news. I hate to be the nagging one :) but in my opinion:

1) EF is missing crucial part regarding stored procedures - multiple result sets.

2) how do one (easily) map complex type, returned from sp, to entities/entity type?

#2 Julie on 8.02.2009 at 7:03 AM

@onemenny - The EF team has an extension that allows multiple result sets which was written for v1. Check http://code.msdn.microsoft.com/EFExtensions. Not sure what the scoop is w/EF4 on this.

#2 - see step # 2 of this post http://thedatafarm.com/blog/data-access/implement-select-stored-procedures-that-return-miscellaneous-data-in-ctp2-of-ef-designer/.

#3 Gurb on 8.10.2009 at 8:21 AM

Do you know if this will work with POCO's? If so will the same limitations apply or will there be others?

#4 Julie on 8.10.2009 at 8:31 AM

Gurb

Not sure which feature you are asking about. The one in my blog post or one of the two asked by onemenny.

Let me know.

julie

#5 GuyBehindtheGuy on 9.18.2009 at 11:26 AM

Julie,

Is this available in the .NET Framework 4 Beta 1 bits? Or do we need to wait until Beta 2?

#6 Julie on 9.18.2009 at 11:53 AM

Beta1 :)

#7 D. Lambert on 11.05.2009 at 1:29 PM

If anyone has tried the combination of complex types sets + multiple result sets, this is the "killer combo" I'm waiting for in order for EF to truly be useful for me.

I understand that the extensions provide support for multiple result sets (I played with it briefly w/ the current EF), but I believe I really need designer support for it -- otherwise I can only get a complex type generated for the first result set returned by my proc, correct?

Overall, this truly looks like progress in the right direction, but it's frustrating to see multiple result sets left out of the designer yet again.

#8 Dwain on 3.21.2010 at 5:02 PM

How do you call a stored procedure and pass in parameters?

#9 Julie on 3.21.2010 at 5:07 PM

@dwain

if the sproc has parameters then the function will be created with those parameters and you can just pass them in.

Make sense or do you need an example?

#10 Victor on 3.25.2010 at 4:27 PM

Is it possible to import a SQL function instead of a stored procedure?

The dropdown list in the "Add Function Import" dialog only lists stored procedures. I had hoped the title of this dialog literally meant "function import".

#11 Wim on 4.01.2010 at 6:57 PM

Great article but could you pls explain how to proceed when I want to bind the data of the stored procedure to a datagrid.

Thx in advance

#12 Arul on 4.13.2010 at 10:40 AM

Function Import and SelfTracking entities or POCO is not working as expected. Any work around?

#13 Julie on 4.13.2010 at 10:47 AM

Hi @arul

Try here:

social.msdn.microsoft.com/.../threads

Leave a Comment