Entities in Entity Framework

Entities in Entity Framework

In this article, I am going to discuss the Entities in Entity Framework with examples. Please read our previous article where we discussed Entity Framework Context Class in Detail. At the end of this article, you will understand the following pointers.

  1. What is an Entity in Entity Framework?
  2. Understanding Scalar Property and Navigation Property
  3. Types of Entities in Entity Framework
  4. POCO Entities
  5. Dynamic Proxy Entities
  6. How to get the Entity Type from the Proxy Type
What is an Entity in Entity Framework?

An entity in Entity Framework is a class that is included as a DbSet<TEntity> type property in the derived context class. Entity Framework maps each entity to a table and each property of an entity to a column in the database. We are going to work with the same example, that we worked on in our previous article. Let’s see the Solution of the console application that we created in the Introduction to Entity Framework article of this article series.

Entities in Entity Framework

The following Department and Employee classes are domain classes in this application.

namespace EFDemo
{
    using System;
    using System.Collections.Generic;
    
    public partial class Department
    {
        [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2214:DoNotCallOverridableMethodsInConstructors")]
        public Department()
        {
            this.Employees = new HashSet<Employee>();
        }
    
        public int ID { get; set; }
        public string Name { get; set; }
        public string Location { get; set; }
    
        [System.Diagnostics.CodeAnalysis.SuppressMessage("Microsoft.Usage", "CA2227:CollectionPropertiesShouldBeReadOnly")]
        public virtual ICollection<Employee> Employees { get; set; }
    }
}

namespace EFDemo
{
    using System;
    using System.Collections.Generic;
    
    public partial class Employee
    {
        public int ID { get; set; }
        public string Name { get; set; }
        public string Email { get; set; }
        public string Gender { get; set; }
        public Nullable<int> Salary { get; set; }
        public Nullable<int> DepartmentId { get; set; }
    
        public virtual Department Department { get; set; }
    }
}

The above Department and Employee classes become entities when they have included as DbSet<TEntity> properties in the context class (the class which is derived from DbContext class).

Let’s open the EF_Demo_DBEntities.cs class which is a context class that looks like below
namespace EFDemo
{
    using System.Data.Entity;
    using System.Data.Entity.Infrastructure;
    public partial class EF_Demo_DBEntities : DbContext
    {
        public EF_Demo_DBEntities()
            : base("name=EF_Demo_DBEntities")
        {
        }
    
        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {
            throw new UnintentionalCodeFirstException();
        }
    
        public virtual DbSet<Department> Departments { get; set; }
        public virtual DbSet<Employee> Employees { get; set; }
    }
}

In the above context class Departments and Employees, properties are of type DbSet<TEntity> which are called entity sets. The Departments and Employees are entities. An Entity can include two types of properties: Scalar Properties and Navigation Properties.

Scalar Property:

The primitive type properties are called scalar properties. Scalar property stores the actual data. A scalar property maps to a single column in the database table. For example: in the Employee class below are the scalar properties

public int ID { get; set; }
public string Name { get; set; }
public string Email { get; set; }
public string Gender { get; set; }
public Nullable<int> Salary { get; set; }
public Nullable<int> DepartmentId { get; set; }

In Department Class Below are the Scalar properties

public int ID { get; set; }
public string Name { get; set; }
public string Location { get; set; }
Navigation Property:

The navigation property represents a relationship to another entity. There are two types of navigation properties:

  1. Reference Navigation
  2. Collection Navigation
Reference Navigation Property:

If an entity includes a property of entity type, it is called a Reference Navigation Property. It represents the multiplicity of one (1). For example: In Employee Class below the property is a Reference Navigation property.

public virtual Department Department { get; set; }

Collection Navigation Property:

If an entity includes a property of collection type, it is called a collection navigation property. It represents the multiplicity of many (*). For example: In the Department class below the property is a collection navigation property.

public virtual ICollection<Employee> Employees { get; set; }

Types of Entities in Entity Framework:

In Entity Framework, there are two types of entities that allow developers to use their own custom data classes together with the data model without making any modifications to the data classes themselves. The two types of Entities are as follows:

  1. POCO entities
  2. Dynamic Proxy entities
POCO Entities

POCO stands for Plain Old CLR Objects which can be used as existing domain objects with your data model. The POCO data classes which are mapped to entities are defined in a data model. A POCO entity is a class that doesn’t depend on any framework-specific base class. It is like any other normal .NET CLR class, which is why it is called “Plain Old CLR Objects”. The POCO entities are supported in both EF 6 and EF Core.

These POCO entities support most of the same query, insert, update, and delete behaviors as entity types that are generated by the Entity Data Model. The following is an example of an Employee POCO entity.

public class Employee
{
    public int ID { get; set; }
    public string Name { get; set; }
    public string Email { get; set; }
    public string Gender { get; set; }
    public Nullable <int> Salary { get; set; }
    public Nullable <int> DepartmentId { get; set; }
    public virtual Department Department { get; set; }
}
Dynamic Proxy Entities 

The Dynamic Proxy is a runtime proxy class that wraps the POCO entity.  A POCO entity should meet the following requirements to become a POCO proxy:

  1. The POCO class must be declared with public access.
  2. A POCO class must not be sealed.
  3. The POCO class must not be abstract.
  4. Each navigation property must be declared as public, virtual.
  5. All the collection property must be ICollection<T>.
  6. The ProxyCreationEnabled option must NOT be false (default is true) in the context class.

Dynamic proxy entities allow lazy loading. Dynamic proxy entities are only supported in EF 6. EF Core 2.0 does not support them yet. If you want the Entity Framework to support lazy loading of the related objects and to track changes in POCO classes, then the POCO classes must meet the following requirements −

  1. Custom data classes must be declared with public access.
  2. Custom data classes must not be sealed and abstract
  3. Custom data classes must have a public or protected constructor that does not have parameters.
  4. Use a protected constructor without parameters if you want the CreateObject method to be used to create a proxy for the POCO entity.
  5. Calling the CreateObject method does not guarantee the creation of the proxy: the POCO class must follow the other requirements that are described in this topic.
  6. The class cannot implement the IEntityWithChangeTracker or IEntityWithRelationships interfaces because the proxy classes implement these interfaces.
  7. The ProxyCreationEnabled option must be set to true.

The following POCO entity meets all of the above requirements to become a dynamic proxy entity at runtime.

public class Employee
{
    public int ID { get; set; }
    public string Name { get; set; }
    public string Email { get; set; }
    public string Gender { get; set; }
    public Nullable <int> Salary { get; set; }
    public Nullable <int> DepartmentId { get; set; }
    public virtual Department Department { get; set; }
}
Get the Entity Type from the Proxy Type:

We can find the original or actual entity type from this proxy type using the GetObjectType method of ObjectContext. This is a static method so there is no need to create an object of the object context.

namespace EFDemo
{
    class Program
    {
        static void Main(string[] args)
        {
            using (EF_Demo_DBEntities DBEntities = new EF_Demo_DBEntities())
            {
                var employee = DBEntities.Employees.Find(1);
                var employeeType = ObjectContext.GetObjectType(employee.GetType());       
                Console.WriteLine("FullName of Employee Master Type :" + employeeType.FullName);
                Console.ReadKey();
            }
        }
    }
}

The GetObjectType returns an actual entity type even if we pass the instance of entity type (not the proxy type). In short, we can always use this method to get the actual entity type, there is no need to check whether the type is a proxy type or not.

Note: By default, the dynamic proxy is enabled for every entity. However, you can disable dynamic proxy in the context by setting this.Configuration.ProxyCreationEnabled = false; as shown below

namespace EFDemo
{
    using System.Data.Entity;
    using System.Data.Entity.Infrastructure;
    public partial class EF_Demo_DBEntities : DbContext
    {
        public EF_Demo_DBEntities()
            : base("name=EF_Demo_DBEntities")
        {
            this.Configuration.ProxyCreationEnabled = false;
        }
    
        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {
            throw new UnintentionalCodeFirstException();
        }
        
        public virtual DbSet<Department> Departments { get; set; }
        public virtual DbSet<Employee> Employees { get; set; }
    }
}

In the next article, I am going to discuss the Entity States in Entity Framework. Here, in this article, I try to explain Entities in the Entity Framework. I hope this article will help you with your need. I would like to have your feedback. Please post your feedback, question, or comments about this article.

5 thoughts on “Entities in Entity Framework”

Leave a Reply

Your email address will not be published. Required fields are marked *