本随笔只是个人学习笔记记录
说明:本文采用asp.netcore 3.1 空的web项目演示EFCore以及数据库迁移,数据库使用vs2019自带的localdb。
一、EFCore 支持主流关系型数据库
EFCore 支持主流关系型数据库,包括sqlserver,vs 自带的localdb,oracle,mysql,sqllite,postgresql,db2等。对于不同的关系型数据库,EFCore 都提供了相应
的提供程序(Provider),详情请参考官网: https://docs.microsoft.com/zh-cn/ef/core/providers/?tabs=dotnet-core-cli
二、数据库上下文DbContext,定义与数据库映射的Entity
EFCore 通过 DbContext 与数据库建立连接,其对应关系如下图所示:一个DbSet<T> 对应一张表,表的字段,就是类T的属性。
1.使用DbContext 之前,先nuget 添加如下安装包:
2.定义Entity(与数据库对应的实体)Student 如下:
public class Student
{
public int Id { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
public DateTime Birthday { get; set; }
public string Gender { get; set; }
}
3.继承DbContext 类如下:
public class MyDataContext:DbContext
{
/// <summary>
/// 配置MyDataContext,配置怎么连接到哪个数据库;使用依赖注入来创建具体的MyDataContext对象。
/// (在 StartUp类的ConfigureServices中注入。)
/// </summary>
/// <param name="options"></param>
public MyDataContext(DbContextOptions<MyDataContext> options):base(options)
{
}
public DbSet<Student> Students { get; set; }
}
4.需要将DbContext 注册服务(依赖注入):
public class Startup
{
private readonly IConfiguration configuration;
/// <summary>
/// 构造函数注入,运行时 会自动注入 _configuration;
/// </summary>
/// <param name="_configuration"></param>
public Startup(IConfiguration _configuration)
{
configuration = _configuration;
}
public void ConfigureServices(IServiceCollection services)
{
var connstr = configuration["ConnStrs:LocalConnStr"];//获取配置文件AppSetting.json中的数据库连接字符串。
//配置服务,依赖注入
services.AddDbContext<MyDataContext>( options=> {
options.UseSqlServer(connstr);
});
//注册服务
services.AddScoped<IRepository<Student>, StudentRepository>();
}
public void Configure(IApplicationBuilder app, IWebHostEnvironment env)
{
if (env.IsDevelopment())
{
app.UseDeveloperExceptionPage();
}
app.UseRouting();
app.UseEndpoints(endpoints =>
{
endpoints.MapGet("/", async context =>
{
await context.Response.WriteAsync("Hello World!");
});
});
}
}
5、存储层使用DbContext 如下:利用DbContext,对数据库的数据进行增删改查。
接口:
public interface IRepository<T> where T:class
{
IEnumerable<T> GetAll();
IEnumerable<T> GetEntities(Expression<Func<T,bool>> exp);
T GetById(int Id);
void Add(T Entity);
void Modified(T Entity);
void Delete(T Entity);
}
实现类:
public class StudentRepository : IRepository<Student>
{
private readonly MyDataContext context;
public StudentRepository(MyDataContext _context)
{
context = _context;//通过构造函数注入,已经在ConfigureServices进行注册了
}
public void Add(Student Entity)
{
context.Students.Add(Entity);
context.SaveChanges();
}
public void Delete(Student Entity)
{
context.Remove(Entity);
}
public IEnumerable<Student> GetAll()
{
return context.Students.ToList();
}
public Student GetById(int Id)
{
return context.Students.Find(Id);
}
public IEnumerable<Student> GetEntities(Expression<Func<Student,bool>> exp)
{
return context.Students.Where(exp);
}
public void Modified(Student Entity)
{
throw new NotImplementedException();
}
}
三、数据迁移:实现Entity与数据库的映射。
数据迁移,即将程序中DbContext的实体类,映射到数据库中。具体而言就是根据DbContext中的实体类,在数据库中创建表、更改表结构等(即根据Entity,在数据库中设计表)。
迁移主要用到两个命令:Add-Migration xxx 和 Update-Database。可通过 vs自带的 Package Manage Console 工具执行这两个命令完成迁移。
1.Add-Migration xxx 命令:添加迁移,xxx为描述性单词。如果数据库还没有创建,则会创建一个迁移文件夹 Migrations,迁移文件夹中包含迁移类和快照类。
每次执行迁移文件夹中包含则会生成一个迁移类和一个快照类,每次执行 Add-Migration 都会生成一个迁移类,而快照类只有一个。
迁移类的代码,就是对应创建数据库的代码(或者更新数据库的代码)。
2.Update-Database 命令:这个命令会使用迁移类的代码,将其转换成sql语句,然后执行到目标数据库。执行成功后,数据库中的表就会和DbContext中的Entity一一对应。如果更新了DbContext中Entity的设计,则再此执行 Add-Migration 和 Update-Database即可,此时会另外生成迁移类,但快照类只有一个。
3.命令实操:数据库使用VS2019自带的localdb.
操作时,如果报异常,请参考 和 处理。
3.1 配置LocalDB数据库连接:
视图—> SQL Server 对象资源管理器,选则数据库实例,鼠标右键属性获取数据库连接字符串。
将数据库连接字符串,放入配置文件中,并更改连接的数据库名称(后面执行完命令后,数据库会自动创建)
配置好后,就能通过IConfiguration获取了。
{
"Logging": {
"LogLevel": {
"Default": "Information",
"Microsoft": "Warning",
"Microsoft.Hosting.Lifetime": "Information"
}
},
"AllowedHosts": "*",
"ConnStrs": {
"LocalConnStr": "Data Source=(localdb)\\MSSQLLocalDB;Initial Catalog=FyyTestDB;Integrated Security=True;Connect Timeout=30;Encrypt=False;TrustServerCertificate=False;ApplicationIntent=ReadWrite;MultiSubnetFailover=False"
}
}
3.2 执行 Add-Migration xxx命令:打开 vs2019->工具->nuget包管理器->程序包管理器控制台 执行命令
执行Add-Migration 命令后,文件生成如下:其中带时间戳的就是迁移文件。
3.3 执行 Update-Database 命令,根据迁移类的代码,执行到目标数据库。
执行完后,数据库及DbContext中Entity 对应的表就已经创建好了。
其中,EFMigrationsHistory 表记录了每一次迁移。