开复学生网,圣徒下载,剑心仙缘
有两种方式来实现数据库映射:
有继承关系的实体如何映射?
就是把父类和子类生成同一张表,额外增加了一列discriminator字段,区分是父类或子类的数据类型
比如:
父类book对象
public class book { [key] [databasegenerated(databasegeneratedoption.identity)] public int bookid { get; set; } public string bookname { get; set; } public int pages { get; set; } }
子类historybooks对象,继承book
public class historybooks:book { public int chapter { get; set; } }
数据库生成一张表
不管父类子类,各自生成一张表,以及在子类中增加两者联系的外键;
定义tpt方式 父类和子类定义 [table("xxx")]
如:
父类
[table("book")] public class book { [key] [databasegenerated(databasegeneratedoption.identity)] public int bookid { get; set; } public string bookname { get; set; } public int pages { get; set; } }
子类
[table("historybooks")] public class historybooks:book {public int chapter { get; set; } }
映射数据生成的两张表
book:
historybooks:
给实体对象的属性加上注解特性,实现与数据库之间建立映射关系并进行控制
如:
booid映射到表中字段为自增的主键
dataannotations 包含的常用特性:
keyattribute:对应数据库中表的主键的设置
requiredattribute:对应数据库中字段的数据不可null
maxlengthattribute:对应数据库中字符串类型字段的最大长度
concurrencycheckattribute:指定用于开放式并发检查的列的数据类型
timestampattribute:将列的数据类型指定为行版本
databasegeneratedattribute:标记指定实体属性是由数据库生成的,并指定生成策略(none数据库不生成值,identity当插入行时,数据库生成值,computed当插入或更新行时,数据库生成值)
tableattribute:指定实体类对应的数据表名
columnattribute:指定实体属性在数据库中的列名
foreignkeyattribute :指定导航属性的外键字段
notmappeattribute:不映射对应字段
fluent api的配置方式可以将实体类与映射配置进行解耦合
有两种方式来实现fluent api的映射配置
如下面的book类,不再有data annotation特性
public class book { public int bookid { get; set; } public string bookname { get; set; } public int pages { get; set; } }
重写dbcontext中的onmodelcreating方法实现book类映射的配置:
protected override void onmodelcreating(dbmodelbuilder modelbuilder) { modelbuilder.entity<book>().haskey(t => t.bookid); base.onmodelcreating(modelbuilder); }
现实项目中,实体对象可能是非常多的,在onmodelcreating方法中逐一进行映射配置,可想而知会造成dbcontext的代码庞大。
1、在新建的bookmap类实现映射配置
public class bookmap : entitytypeconfiguration<book> { public bookmap() { this.totable("book", "dbo"); this.haskey(p => p.bookid); //this.haskey(p => new { p.bookid, p.bookpreid });//关联主键 this.property(p => p.bookid).hasdatabasegeneratedoption(databasegeneratedoption.identity);//自动生成 this.property(p => p.bookname).isrequired().hasmaxlength(20).hascolumnname("bookname").isunicode(false);//非空,最大长度20,自定义列名,列类型为varchar而非nvarchar this.ignore(p => p.bookdescription);//忽略改属性的映射 } }
2、依旧重写dbcontext中的onmodelcreating方法,将bookmap 类的实例添加到modelbuilder的configurations。
protected override void onmodelcreating(dbmodelbuilder modelbuilder) { modelbuilder.configurations.add(new bookmap()); }
这样能大大减少onmodelcreating的代码量,依然存在一个问题,就是实体对象一多,还是要逐条将map类的实例添加到modelbuilder的configurations
3、利用反射将程序集中所有的entitytypeconfiguration添加到modelbuilder.configurations中,可以说完全解耦了
protected override void onmodelcreating(dbmodelbuilder modelbuilder) { var typestoregister = assembly.getexecutingassembly().gettypes() .where(type => !string.isnullorempty(type.namespace)) .where(type => type.basetype != null && type.basetype.isgenerictype && type.basetype.getgenerictypedefinition() == typeof(entitytypeconfiguration<>)); foreach (var type in typestoregister) { dynamic configurationinstance = activator.createinstance(type); modelbuilder.configurations.add(configurationinstance); } }
注:此段代码源自网友文章,摘自nopcommerce项目的代码
如对本文有疑问,请在下面进行留言讨论,广大热心网友会与你互动!! 点击进行留言回复
Net Core Web Api项目与在NginX下发布的方法
asp.net core3.1 引用的元包dll版本兼容性问题解决方案
IdentityServer4实现.Net Core API接口权限认证(快速入门)
ASP.NET Core MVC通过IViewLocationExpander扩展视图搜索路径的实现
网友评论