Home > dotnet 4, Entity Framework > POCO and Entity Framework

POCO and Entity Framework

I have been playing around with Entity Framework 4 and was intrigued by the POCO support in it, as the new version is CTP 4.0 and we might be approaching the RTM version soon so I thought i will collate my experiences and gotchas on how to use them.

All the code I am going to write to use POCO with EF 4.0 is not part of the Entity Framework 4.0 or VS2010 and in order to use POCO classes with EF4 you have to download the CTP 4.0 which is available here.

Interesting thing is that most of the thing works on Convention over configuration but to see the bigger picture of how things work I am going to break down the development into 4 major steps and how they connected.

  • Create your entity i.e. simple POCO class like Customer,Employee etc
  • For that entity create a corresponding Configuration class
  • Create your data context class
  • Use the ModelBuilder class and tie all the above things together

You must be thinking what the hell is that ?? and that’s exactly I felt it when I first started looking over these things. Lets take things one step at a time.

This is how my project structure looks like and remember it is just a quick proof on concept and not a “Production ready” code. :).

POCO Test project structure

As you can see I created a Class library POCOLibrary.Model and inside this project Customer.cs represent the Domain object , CustomerConfiguration.cs is configuration file and the Northwind.cs is the data context class which talks to the database.

For simplicity I am going to get list of customers from the Customer table.

Customer.cs

namespace PocoLibrary.Model
{
    public class Customer
    {
        public string CustomerId { get; set; }
        public string CompanyName { get; set; }
        public string ContactName { get; set; }
        public string ContactTitle { get; set; }
        public string Address { get; set; }
        public string City { get; set; }
        public string Region { get; set; }
        public string PostalCode { get; set; }
        public string Country {get;set;}
        public string Phone { get; set; }
        public string Fax { get; set; }
    }
}

CustomerConfiguration.cs

using System.Data.Entity.ModelConfiguration;

namespace PocoLibrary.Model
{
    public class CustomerConfiguration : EntityConfiguration<Customer>
    {
        public CustomerConfiguration()
        {
            this.HasKey(c => c.CustomerId);
            this.Property(c => c.ContactName).IsRequired();
        }
    }
}

As you can see we have a reference to a new namespace ModelConfiguration and by using the EntityConfiguration class we are saying that for Customer Entity we have a corresponding configuration class which will describe how this entity is represented in our database.

Then we are mapping the CustomerId property of our domain object to our customer table primary key.The beauty of the above 2 classes is that there is no database specific code, in fact our domain object represents a pure domain object it doesn’t inherit or implements any database specific classes or interfaces.

Northwind.cs

using System.Data.Entity;
using System.Data.Entity.Infrastructure;

namespace PocoLibrary.Model
{
    public class Northwind : DbContext
    {
        public Northwind(DbModel mode) : base(mode)
        {
            Database.SetInitializer<Northwind>(null);
        }
        public DbSet<Customer> Customer { get; set; }
    }
}
 

This is data context class which inherits from DbContext and not from ObjectContext(when you create a model from database it uses ObjectContext) and contains the DBSet container for our domain object.

One gotchas I got from using it that you have to use the Database.SetInitializer with a null object otherwise EF think that there is discrepancy between the object and its data store.

You typically get an exception like …


The model backing the ‘Northwind’ context has changed since the database was created.  Either manually delete/update the database, or call Database.SetInitializer with an IDatabaseInitializer instance.  For example, the RecreateDatabaseIfModelChanges strategy will automatically delete and recreate the database, and optionally seed it with new data.


and it took me a while to figure this one out.

Lets start with the last bit i.e. the ModelBinder this is the class which ties up all the above three things together. This is the class responsible for adding the configuration to its configurations collection mapping that to the entitiy and create a Model object which then gets passed to the constructor of the DbContext class.

To illustrate how it works I have created a simple ASP.NET MVC in which I created a CustomerController (again convention over configuration) and created a view called Index.aspx and strongly type it our Customer domain object.

This is how my Index method of Customer Controller class looks like.

CustomerController.cs

namespace POCOTest.Controllers
{
    public class CustomerController : Controller
    {

        // GET: List of Customers/
        public ActionResult Index()
        {
            var builder = new ModelBuilder();
            builder.Configurations.Add(new CustomerConfiguration());
            builder.Entity<Customer>();

            var model = builder.CreateModel();
            IQueryable<PocoLibrary.Model.Customer> customers;

            var context = new Northwind(model);
           
            customers = from c in context.Customer select c;
            ViewData.Model = customers;
           
            return View();
        }

      }

}

As i said this is just an illustration and no way your controller should be invoking datacontext object directly, also I would like to point in out that although Linq to SQL or Lind to Entity makes things quite easier for you but you shouldn’t be returning IQueryable from your queries as it would really harm the performance of your application due to delayed execution and lazy loading.

It’s all good, everything ready, is it good to go ?? but we are missing one small bit isn’t it ?? and yes you have guess it right where the hell is the connection string and where we are passing it ? and the answer is again convention over configuration … i.e. if you add a connection string which matches the name of your DbContext class then it will automatically pick that string and use it out of the box. So this is how the connection string looks in my web.config file.

<connectionStrings>

    <add name="Northwind"
        connectionString="Data Source=.\DB;Initial Catalog=Northwind;Integrated Security=SSPI;"
        providerName="System.Data.SqlClient" />
  </connectionStrings>

All I did is created a strong type view based on list of Customer and run the app to populate the list of customers.

List of Customers

Please feel free to comment or get in touch if you want the source code.

Advertisements
  1. Gorang
    September 16, 2010 at 6:20 am

    nice one this is what i was looking for

    plz share code as well

    keep up the good work

    • September 17, 2010 at 10:15 pm

      No worries hope this helps and I will see if I can come up with more complex and real world scenarios for this.

  2. tfannon
    October 15, 2010 at 1:34 am

    can you share the code for the simple example?
    thank you.
    TF

    • October 18, 2010 at 6:11 am

      Sorry I was away, I have send you the code. Feel free to contact me on my email if you have problems with the code…

  3. Karim
    October 30, 2010 at 7:32 pm

    Can you share the code for this example?
    Thank you
    Kind Regards
    Karim

    • October 31, 2010 at 11:18 pm

      I have send you the code and let me know if you have any problems in running the sample.

  4. Vijay
    November 30, 2010 at 3:20 pm

    As a Newbie, I am always searching online for articles that can help me. Thank you Wow! Thank you! I always wanted to write in my site something like that. Can I take part of your post to my blog?

  5. November 30, 2011 at 2:41 am

    Hi prashantb!
    it is a good article.
    Can you send source code for this article?
    Thank

  6. Nawaz
    April 23, 2012 at 9:41 am

    Hi Prashanth,

    Good Article , Can you please send code ??

    Thanks …

    • May 3, 2012 at 8:52 pm

      Hi Nawaz,
      I have send you the source code and let me know how it goes.

  1. March 15, 2011 at 8:53 pm
  2. April 6, 2011 at 8:17 pm

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s

%d bloggers like this: