Configure Many-to-Many Relationships in Entity Framework Core Code First

In RDBMS, we call a relationship between two tables many to many when more than one record in one table is associated with multiple records in the other table. Consider two tables named Employees and Skills. A skill can be associated with more than one employee, and one employee can have more than one skill. It is a typical example of a many-to-many relationship. A join table is required to represent this relationship in the database.

Let us check how a many-to-many relationship between two entities named Employee and Skill can be configured in EF Core 5.0

    public class Employee
    {
        public int id { get; set; }
        public string Name { get; set; }
        public string Address { get; set; }
        /* Collection property of Skills */
        public ICollection<Skill> Skills { get; set; }
    }
 public class Skill
    {
        public int id { get; set; }
        public string SkillName { get; set; }
        /* Collection property of Employees */
        public ICollection<Employee> Employees { get; set; }
    }



A many-to-many relationship is defined here by including a collection property of Skill in Employee entity and a collection property of Employee in Skill entity. EF Core will recognize it as a many-to-many relationship and generate a joining table for the same. In AppDbContext class, it is not necessary to have a third DbSet property for the joining table "EmployeeSkill."

 public class AppDbContext : DbContext
    {
        public AppDbContext(DbContextOptions<AppDbContext> options) : base(options)
        { }
        public DbSet<Employee> Employees { get; set; }
        public DbSet<Skill> Skills { get; set; }
    }



In Entity Framework Core 3.x and previous versions, a joining table definition is necessary to create a many-to-many relationship. In addition to that, Fluent API is used to define the composite primary key. The following code creates a many-to-many relationship if you use Entity Framework Core 3.x or the previous versions.

 public class Employee
    {
        public int id { get; set; }
        public string Name { get; set; }
        public string Address { get; set; }
        public ICollection<EmployeeSkill> EmployeeSkills { get; set; }
    }
  public class Skill
    {
        public int id { get; set; }
        public string SkillName { get; set; }
        public ICollection<EmployeeSkill> EmployeeSkills { get; set; }
    }
 public class EmployeeSkill
    {
        public int SkillId { get; set; }
        public int EmployeeId { get; set; }
        public Employee Employee { get; set; }
        public Skill Skill { get; set; }
    }

The above 3 entity classes are necessary to create a many-to-many relationship. Note that a collection property of the joining table is added to the Employee and the Skill entities. A composite primary key is defined using the Fluent API.

  public class AppDbContext:DbContext
    {
        public AppDbContext(DbContextOptions<AppDbContext> options):base(options)
        {  }
        public DbSet<Employee> Employees { get; set; }
        public DbSet<Skill> Skills { get; set; }    
        protected override void OnModelCreating(ModelBuilder modelBuilder)
        {
            modelBuilder.Entity<EmployeeSkill>().HasKey(ES => new { ES.EmployeeId, ES.SkillId });
        }

    }

Check out the next article to learn about CRUD (create, read, update, Delete) operations using EF Core on tables connected through a many-to-many relationship.


Search