MVC5 EF6 入门完整教程八.docx
- 文档编号:29802589
- 上传时间:2023-07-27
- 格式:DOCX
- 页数:7
- 大小:17.03KB
MVC5 EF6 入门完整教程八.docx
《MVC5 EF6 入门完整教程八.docx》由会员分享,可在线阅读,更多相关《MVC5 EF6 入门完整教程八.docx(7页珍藏版)》请在冰豆网上搜索。
MVC5EF6入门完整教程八
MVC5+EF6入门完整教程八
本篇是相对独立的一篇,主要讲解不丢失数据进行数据库结构升级。
前面我们讲解EF功能时(见第三篇文章)已经介绍过一种更新数据库的方式:
EF比较model和database,如果两边不一致,程序将会dropandre-create数据库。
本篇文章我们会使用codefirstmigrations的方式。
这个功能可以使你改变datamodel,在不dropandre-create数据库的情况下更新数据库的结构,将这些改变部署到生产环境中。
下面就着重介绍如何使用此功能。
文章提纲
前置条件
启用迁移功能
执行迁移
总结
前置条件
先回顾下之前EF修改模型的方式。
我们事先配置好EF,每次数据模型改变的时候都会dropandre-create数据库。
例如你增加、删除、改变实体类,或改变DbContext类后,运行程序时将会自动删除已有的数据库,创建一个新数据库来匹配修改后的模型,同样也会根据Seed方法中内容新建testdata.
这种保持database和datamodel同步的方法在开发阶段很方便。
如果已经部署到生产环境中就不行了,例如表中扩充一些字段啥的,原来的数据就不能丢失。
我们禁用原来更新数据库的方式,将web.config中contexts配置节注释掉。
另外我们不用原来数据,改下数据库名,这样可以生成一个新的数据库,方便做实验。
启用迁移
下面就启用CodeFirstMigrations来解决数据库更新的问题。
打开PackageManagerConsole连续输入如下指令:
enable-migrations和add-migrationInitialCreate
enable-migrations指令:
a.在项目根目录下创建了一个Migrations文件夹
b.在Migrations文件夹下新建一个Configuration.cs文件。
可以通过修改Configuration.cs来对Migration做一些配置(如加入一些测试数据等)
Note
如果前面没修改web.config的数据库名,执行enable-migrations指令后,Migrations将会找到已有的数据库MVCDemo然后自动执行add-migration指令。
类似我们第三篇文章中讲到DALàAccountInitilizer.cs类,Configuration类也包含一个Seed方法。
当数据库新建或数据库结构更新后,这个方法会被调用,利用这个方法可以插入或更新testdata.配置Seed方法
使用dropandre-create的方式时,因为每次model改变时数据库都会被删除,所有数据都会丢失,所以需要使用DALàAccountInitilizer.cs的Seed方法来插入测试数据。
使用CodeFirstMigrations方式,当数据库改变时测试数据会保留,所以包含testdata的Seed方法一般来说是不需要的。
如果我们要部署数据库到生产环境,事实上这种情况下我们也不想Seed方法来插入测试数据到生产环境中。
生产环境中用到Seed方法的例子:
比如在我们部署时获得了实际的初始化数据,如实际存在的组织部门这些初始化的信息。
我们为了做实验方便,还是插入一些测试数据。
先插入SysUser和SysRole
类似于前面文章提到的,Seed方法接收一个databasecontext参数,利用这个参数添加新的实体到数据库中。
对每个实体类型:
新建一个实体集合
添加到相应的DbSet属性
保存更改到数据库中
如果大家还记得之前的文章可以发现有一点不同,以前都是用Add方法,这次用了AddOrUpdate方法来插入数据。
sysUsers.ForEach(s=>context.SysUsers.AddOrUpdate(p=>p.UserName,s));
每次执行update-databse指令时都会执行Seed方法,一般来说,每次迁移后,你不仅仅是插入数据,例如你想要插入的数据在你创建数据库的第一次迁移后已经在数据库中了,这种情况下更新原有数据就可以了。
AddOrUpdate正好可以解决这个问题:
如果数据不存在,插入数据;如果数据存在,更新这笔数据。
context.SysUsers.AddOrUpdate(p=>p.UserName,s)
第一个参数p.UserName就是检查数据是否存在的主键。
我们的测试数据中,假设UserName都不能重复。
作为比较,我们添加SysUserRole实体类型的时候没有使用AddOrUpdate,直接人为判断是否存在,不存在再插入。
编译下项目,下面开始更新数据库。
执行迁移
前面执行add-migration时,同样在Migrations文件夹里面,产生一个<timestamp>_InitialCreate.cs的文件。
里面两个方法,Up和Down:
Up方法创建数据库表,Down方法删除表。
publicoverridevoidUp()
{
CreateTable(
"dbo.SysRole",
c=>new
{
ID=c.Int(nullable:
false,identity:
true),
RoleName=c.String(),
RoleDesc=c.String(),
})
.PrimaryKey(t=>t.ID);
CreateTable(
"dbo.SysUserRole",
c=>new
{
ID=c.Int(nullable:
false,identity:
true),
SysUserID=c.Int(nullable:
false),
SysRoleID=c.Int(nullable:
false),
})
.PrimaryKey(t=>t.ID)
.ForeignKey("dbo.SysRole",t=>t.SysRoleID,cascadeDelete:
true)
.ForeignKey("dbo.SysUser",t=>t.SysUserID,cascadeDelete:
true)
.Index(t=>t.SysUserID)
.Index(t=>t.SysRoleID);
CreateTable(
"dbo.SysUser",
c=>new
{
ID=c.Int(nullable:
false,identity:
true),
UserName=c.String(),
Email=c.String(),
Password=c.String(),
})
.PrimaryKey(t=>t.ID);
}
publicoverridevoidDown()
{
DropForeignKey("dbo.SysUserRole","SysUserID","dbo.SysUser");
DropForeignKey("dbo.SysUserRole","SysRoleID","dbo.SysRole");
DropIndex("dbo.SysUserRole",new[]{"SysRoleID"});
DropIndex("dbo.SysUserRole",new[]{"SysUserID"});
DropTable("dbo.SysUser");
DropTable("dbo.SysUserRole");
DropTable("dbo.SysRole");
}
下面我们就执行正式迁移。
打开PackageManagerConsole
输入update-database
update-database指令调用了Up方法来新建database的表(和datamodelentityset对应),然后调用Seed方法来填充测试数据。
这个时候测试下程序,打开数据库看下,完全符合我们的预期。
再进一步,我们添加一个表Test
先添加一个Model
修改AccountContext.cs,增加一个datamodelentityset
执行add-migrationAddTestTable和update-database,完成数据库表的添加。
去数据库中检查,发现已经多了Test这张表了。
最后再检查下新产生的配置文件。
大家现在应该能充分理解到add-migration时产生的文件的作用了吧。
总结
本次我们主要讲解了数据库迁移/升级的问题。
主要分为启用迁移(enable-migrations)和执行迁移(add-migration,update-database)两大步骤。
启用迁移:
产生迁移相关文件夹Migrations和文件夹中相关的配置文件。
执行迁移:
产生相关的迁移更改文件并执行更改。
请充分理解本篇文章所讲的例子,后面文章会多次用到add-migration.
好了,今天就到这里。
欢迎大家多多评论,让下一篇文章更好:
)
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- MVC5 EF6 入门完整教程八 入门 完整 教程