Code First approach provides two methods to configure the domain classes of application: using Data Annotations and using the Fluent API. Data Annotations only give us a subset of configuration options. Fluent API provides a full set of configuration options available in Code-First. Fluent API provides more functionality for configuration than Data Annotations. In this article we will read about the Fluent API.
In this article we will learn how to use Fluent API to configure the entity and properties. First we create Employee and Project domain class and also create a content class.
Employee Domain Class:
- class Employee
- {
- public int Emp_Id { get; set; }
- public string Emp_Name { get; set;}
- public string Deparment { get; set; }
- public int Number_Of_Projects { get; set; }
- public Project Project { get; set; }
-
- }
Project Domain Class
- class Project
- {
- public int Project_Id { get; set; }
- public string Project_Name { get; set; }
- public string Project_Head { get; set; }
- public DateTime DeadLIne { get; set; }
- public ICollection<Employee> Employees { get; set; }
- }
EmployeeContext Class
- class EmployeeContext:DbContext
- {
- public EmployeeContext() : base()
- {
-
- }
- public DbSet<Employee> Employees { get; set; }
- public DbSet<Project> Projects { get; set; }
-
- protected override void OnModelCreating(DbModelBuilder modelBuilder)
- {
-
-
- base.OnModelCreating(modelBuilder);
- }
- }
Following is the database for above domain classes.
The EmployeeContext class overrides the OnModelCreating method of DBContext class. Now all configuration code for Fluent API will be written in OnModelcreating method . This Method contain a parameter of DbModelBuilder class, this is the main class used for configuring the all domain classes. DbModelBuilder class includes important properties and methods to configure.
EntityTypeConfiguration Class :
EntityTypeConfiguration class is most important class in Fluent API that allows configuration to be performed for an entity type in a model. An EntityTypeConfiguration<TEntityType> can be obtained by using the Entity method on DbModelBuilder or a custom type derived from EntityTypeConfiguration<TEntityType> can be registered by using the Configurations property on DbModelBuilder.
Use EntityTypeConfiguration
Use DbModelBuilder
EntityTypeConfiguration contain the following methods
Method | Description |
Equals | Determines whether the specified object is equal to the current object. |
GetHashCode | Serves as a hash function for a particular type. |
GetType | Gets the type of the current instance. |
HasEntitySetName | Configures the entity set name to be used for this entity type. |
HasKey<TKey> | Configures the primary key property(s) for this entity type. |
HasMany<TTargetEntity> | Configures a many relationship from this entity type |
HasOptional<TTargetEntity> | Configures an optional relationship from this entity type. |
HasRequired<TTargetEntity> | Configures a required relationship from this entity type. |
Map<TDerived>(Action<EntityMappingConfiguration<TDerived>>) | Allows advanced configuration related to how a derived entity type is mapped to the database schema. |
Property<T>(Expression<Func<TStructuralType, T>>) | Configures a struct property that is defined on this type. |
ToString | Returns a string that represents the current object. |
ToTable(String) | Configures the table name that this entity type is mapped to. |
ToTable(String,String) | Configures the table name that this entity type is mapped to. |
Entity Mapping:
Now we will learn how to configure the entity using the Fluent API. Entity mapping is a simple approach that explains how the domain classes will map to the database. Let us take some example of entity mapping.
Default Schema
The default schema of database is “dbo” but you can change the default schema from “dbo” to another schema.
To change the schema use the “HasDefaulSchema” method in “OnModel Creating” method as below.
Map Entity To Table:
With default convention of Code First, it will create the database tables with the name of DbSet properties in the context class. So Code First creates the Table with “Employee” and “Project” name. But we can change the name of table and their schema also let us take some examples.
Change the names of tables.
After above query now My_Company database will look like below.
We can see that name of tables are changed, in the same way we can also change the schema of tables.
After above query schema of tables we will change .
Entity Splitting
Using splitting we can divide the entity into multiple tables , in other words we can combine the result coming from multiple tables into a single class. But it is only possible for one to one relationships. The following example shows split Employee entity to multiple tables in the database.
Database
We can see that in the database two new tables are generated Employee_Tab(Emp_Id, Number_Of_Projects) and Employee_Tab(Emp_Id, Emp_Name).
Let us take an another example.
Database
We can see that now three tables are generated for Employee entity , this happens because we forgot to include the “department” property in mapping so a new table is generated for department entity. So the conclusion is don’t use any property in mapping the new table that will contain the all unused properties or fields.
In previous articles we performed the mapping using the “lambda” operator, Code First approach also provide delegate concept for mapping of entity to database. Let us take an example of mapping using the delegates.
Property Mapping Using fluent API:
Using the property mapping we can configure the property of an entity. We can also map and configure the properties of your domain classes using Fluent API. Now we learn how to configure the property using the property method of DbmodelBuilder class.
Configure the Column:
Using the Fluent API we can change the default configuration of a column like column name, column order, data type , maximum length etc. Let us take an example.
Database:
We can see that Order of Emp_Name column in table is second and length of data is 200 and null is allowed in column as per property defined using the Fluent API.
Configure the Primary Key
When an entity class contains a column name with “ID” postfix then this column will become the primary key for that column but if we don’t define any column with “ID”postfix then error will generate. We can also explicitly define the primary key for a table using the “HasKey” Method.
Database
Configure Concurrency Column:
If we define any column as Concurrency column then this column must be included in where clause for updating and deleting query else error will generate. In below query we define the Emp_Id column as concurrency column so this column must be included in where clause for updating and deleting query. We can achieve this using the IsConcurrencyToken method.
Configure Null and NotNull column for property:
In code first approach primitive data type property generates a not null column and reference type property generate nullable column. But we can explicitly define the column as nullbale or not nullable. The Isoptional method is used to define a nullable column and IsRequired method is used to generate the not nullable column.
Define Parameter Name in Stored Procedure:
Using the HasParameterName method we can define the parameter name for a property that will be used in stored procedure.
Thanks for reading the article. If you have any doubt or query related to this topic then mention your query in comment section.