EF Code-First - Ánh xạ thực thể
Ánh xạ thực thể bằng Fluent API
Fluent API có thể được sử dụng để định cấu hình một thực thể để ánh xạ nó với bảng cơ sở dữ liệu, lược đồ mặc định, v.v.
Cấu hình lược đồ mặc định
Đầu tiên, hãy cấu hình một lược đồ mặc định cho các bảng trong cơ sở dữ liệu. Tuy nhiên, bạn có thể thay đổi lược đồ trong khi tạo các bảng riêng lẻ.
Ví dụ sau đặt lược đồ Admin làm lược đồ mặc định. Tất cả các đối tượng cơ sở dữ liệu sẽ được tạo trong lược đồ Quản trị trừ khi bạn chỉ định rõ ràng một lược đồ khác.
public class SchoolContext: DbContext
{
public SchoolDBContext(): base()
{
}
public DbSet<Student> Students { get; set; }
public DbSet<Standard> Standards { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
//Configure default schema
modelBuilder.HasDefaultSchema("Admin");
}
}
Ánh xạ thực thể vào bảng
Code First sẽ tạo các bảng cơ sở dữ liệu với tên của các thuộc tính DbSet
trong lớp Context, trong trường hợp này là Students
và Standards
.
Bạn có thể ghi đè quy ước này và đặt tên bảng khác với các thuộc tính DbSet
, như ví dụ ở bên dưới.
namespace CodeFirst_FluentAPI_Tutorials
{
public class SchoolContext: DbContext
{
public SchoolDBContext(): base()
{
}
public DbSet<Student> Students { get; set; }
public DbSet<Standard> Standards { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
//Configure default schema
modelBuilder.HasDefaultSchema("Admin");
//Map entity to table
modelBuilder.Entity<Student>().ToTable("StudentInfo");
modelBuilder.Entity<Standard>().ToTable("StandardInfo","dbo");
}
}
}
Như bạn có thể thấy trong ví dụ trên, chúng ta bắt đầu với phương thức Entity<TEntity>()
. Hầu như bạn sẽ phải bắt đầu với phương thức Entity<TEntity>()
để định cấu hình bằng Fluent API.
Chúng tôi đã sử dụng phương thức ToTable()
để ánh xạ thực thể Student
vào bảng StudentInfo
và thực thể Standard
vào bảng StandardInfo
.
Lưu ý rằng bảng StudentInfo
nằm trong lược đồ Admin và bảng StandardInfo
nằm trong lược đồ dbo vì chúng tôi đã chỉ định lượng đồ mặc định là Admin và chỉ định lược đồ dbo cho bảng StandardInfo
.
Ánh xạ thực thể vào nhiều bảng
Ví dụ sau đây minh họa cách ánh xạ thực thể Student
vào nhiều bảng trong cơ sở dữ liệu.
namespace CodeFirst_FluentAPI_Tutorials
{
public class SchoolContext: DbContext
{
public SchoolDBContext(): base()
{
}
public DbSet<Student> Students { get; set; }
public DbSet<Standard> Standards { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<Student>().Map(m =>
{
m.Properties(p => new
{
p.StudentId,
p.StudentName
});
m.ToTable("StudentInfo");
}).Map(m =>
{
m.Properties(p => new
{
p.StudentId,
p.Height,
p.Weight,
p.Photo,
p.DateOfBirth
});
m.ToTable("StudentInfoDetail");
});
modelBuilder.Entity<Standard>().ToTable("StandardInfo");
}
}
}
Như bạn có thể thấy trong ví dụ trên, chúng tôi đã ánh xạ một số thuộc tính của thực thể Student
vào bảng StudentInfo
và các thuộc tính khác vào bảng StudentInfoDetail
bằng phương thức Map()
.
Do đó, thực thể Student
sẽ chia thành hai bảng, như hình dưới đây.
Phương thức Map()
yêu cầu một tham số kiểu delegate. Bạn có thể truyền một delegate Action hoặc biểu thức lambda trong phương thức Map()
, như ví dụ bên dưới.
using System.Data.Entity.ModelConfiguration.Configuration;
namespace CodeFirst_FluentAPI_Tutorials
{
public class SchoolContext: DbContext
{
public SchoolDBContext(): base()
{
}
public DbSet<Student> Students { get; set; }
public DbSet<Standard> Standards { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<Student>().Map(delegate(EntityMappingConfiguration<Student> studentConfig)
{
studentConfig.Properties(p => new
{
p.StudentId,
p.StudentName
});
studentConfig.ToTable("StudentInfo");
});
Action<EntityMappingConfiguration<Student>> studentMapping = m =>
{
m.Properties(p => new
{
p.StudentId,
p.Height,
p.Weight,
p.Photo,
p.DateOfBirth
});
m.ToTable("StudentInfoDetail");
};
modelBuilder.Entity<Student>().Map(studentMapping);
modelBuilder.Entity<Standard>().ToTable("StandardInfo");
}
}
}