在上一篇文章我们简单通过一个实例完成对CodeFirst的理解,我们通过实体生成数据库里的表和字段,虽然有一些默认的配置生成规定,但其实我们可以能过对实体进一步控制从而对生成的表字段进行更加符合我们要求的控制;比如主键、非空、范围大小不、字段名称等等;主要有两种方式(1)Data Annotations(2)Fluent API

一:Data Annotations

此方法是利用在实体的那个属性里增加特性来进行操作控制;这些特性是在using System.ComponentModel.DataAnnotations下,要引用DLL

using System.ComponentModel.DataAnnotations;
namespace ModelLib
{
public class Car
{
[Key]
public int ID { get; set; } [Required(ErrorMessage="不能为空")]
public string CarNum { get; set; } [StringLength(,ErrorMessage="最大长度不能超过10个字符")]
public string Colour { get; set; } [Range(,,ErrorMessage="UserYear取证范围在1-10之间")]
public int UserYear { get; set; } [RegularExpression(@"^[\w-]+(\.[\w-]+)*@[\w-]+(\.[\w-]+)+$")]
public string Email { get; set; }
}
}

假如我们代码没有按照上面规定来便会报出异常:

上面只是列出一部分的特性,其它特性可以查MSDN:http://msdn.microsoft.com/zh-cn/library/system.componentmodel.dataannotations.aspx

二:Fluent API(推荐使用,因为前一种范围有限)

1:我们可以在EF上下文里重写OnModelCreating然后对要设置的属性进行操作,但是这样一个实体类如果有3个属性需要配置,10个实体类就需要配置30个,那么就得在OnModelCreating方法里写30行,很麻烦且不易维护,所以一般不这么编写;

using System.Data.Entity;
using ModelLib;
namespace DataLibrary
{
public class MyDbContext : DbContext
{
public MyDbContext()
: base("name=MyTestDb")
{
} protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<Home>().HasKey(d => d.ID);
modelBuilder.Entity<Home>().Property(d => d.Address).IsRequired();
modelBuilder.Entity<Person>().Property(p => p.PassWord).HasMaxLength();
} public DbSet<Person> Person { get; set; } public DbSet<Home> Home { get; set; } public DbSet<Car> Car { get; set; }
}
}

2:注意返回值可以看出modelBuilder的Entity<>泛型方法的返回值是EntityTypeConfiguration<>泛型类。我们可以定义一个继承自EntityTypeConfiguration<>泛型类的类来定义domain中每个类的数据库配置。
ok,我们在DataAccess类库下新建一个继承自EntityTypeConfiguration<>泛型类的DestinationMap类,在构造函数里写上配置:

using System.Data.Entity.ModelConfiguration;
using System.Linq;
using System.Text;
using ModelLib;
namespace DataLibrary
{
public class HomeMap:EntityTypeConfiguration<Home>
{
public HomeMap()
{
Property(d => d.Address).IsRequired();
}
}
}
using System.Data.Entity.ModelConfiguration;
using System.Linq;
using System.Text;
using ModelLib; namespace DataLibrary
{
public class PersonMap:EntityTypeConfiguration<Person>
{
public PersonMap()
{
Property(d => d.Age).IsRequired();
}
}
}

然后修改EF上下文:

using System.Data.Entity;
using ModelLib;
namespace DataLibrary
{
public class MyDbContext : DbContext
{
public MyDbContext()
: base("name=MyTestDb")
{
} protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Configurations.Add(new HomeMap());
modelBuilder.Configurations.Add(new PersonMap());
} public DbSet<Person> Person { get; set; } public DbSet<Home> Home { get; set; } public DbSet<Car> Car { get; set; }
}
}

下面是一些常用的设置:

//【主键】
//Data Annotations:
[Key]
public int DestinationId { get; set; } //Fluent API:
public class BreakAwayContext : DbContext
{
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<Destination>().HasKey(d => d.DestinationId);
}
} //【外键】
//Data Annotations:
public int DestinationId { get; set; }
[ForeignKey("DestinationId")]
public Destination Destination { get; set; } //Fluent API:
modelBuilder.Entity<Lodging>().HasRequired(p => p.Destination).WithMany(p=>p.Lodgings).HasForeignKey(p => p.DestinationId); //【长度】
//Data Annotations:通过StringLength(长度),MinLength(最小长度),MaxLength(最大长度)来设置数据库中字段的长度
[MinLength(),MaxLength()]
public string Name { get; set; }
[StringLength()]
public string Country { get; set; } //Fluent API:没有设置最小长度这个方法
modelBuilder.Entity<Destination>().Property(p => p.Name).HasMaxLength();
modelBuilder.Entity<Destination>().Property(p => p.Country).HasMaxLength(); //【非空】
//Data Annotations:
[Required(ErrorMessage="请输入描述")]
public string Description { get; set; } //Fluent API:
modelBuilder.Entity<Destination>().Property(p => p.Country).IsRequired(); //【数据类型】
Data Annotations:
将string映射成ntext,默认为nvarchar(max)
[Column(TypeName = "ntext")]
public string Owner { get; set; } //Fluent API:
modelBuilder.Entity<Lodging>().Property(p => p.Owner).HasColumnType("ntext"); //【表名】
//Data Annotations:
[Table("MyLodging")]
public class Lodging
{
} //Fluent API
modelBuilder.Entity<Lodging>().ToTable("MyLodging"); //【列名】
//Data Annotations:
[Column("MyName")]
public string Name { get; set; } //Fluent API:
modelBuilder.Entity<Lodging>().Property(p => p.Name).HasColumnName("MyName"); //【自增长】
//Data Annotations
[Key, DatabaseGenerated(DatabaseGeneratedOption.Identity)] Guid类型的主键、自增长
public Guid SocialId { get; set; } //Fluent API:
modelBuilder.Entity<Person>().Property(p => p.SocialId).HasDatabaseGeneratedOption(DatabaseGeneratedOption.Identity); //【忽略列映射】
//Data Annotations:
[NotMapped]
public string Name
{
get
{
return FirstName + " " + LastName;
}
} //Fluent API:
modelBuilder.Entity<Person>().Ignore(p => p.Name); //【忽略表映射】
//Data Annotations:
[NotMapped]
public class Person
{ } //Fluent API:
modelBuilder.Ignore<Person>(); //【时间戳】
//Data Annotations:Timestamp
[Timestamp]
public Byte[] TimeStamp { get; set; } 只能是byte类型 //Fluent API:
modelBuilder.Entity<Lodging>().Property(p => p.TimeStamp).IsRowVersion(); //【复杂类型】
//Data Annotations:
[ComplexType]
public class Address
{
public string Country { get; set; }
public string City { get; set; }
} //Fluent API:
modelBuilder.ComplexType<Address>();

学习EF之CodeFirst二(数据库对应映射)的更多相关文章

  1. 6.翻译系列:EF 6 Code-First中数据库初始化策略(EF 6 Code-First系列)

    原文链接:http://www.entityframeworktutorial.net/code-first/database-initialization-strategy-in-code-firs ...

  2. 学习EF之CodeFirst一

    最近将花点时间学习EF相关知识,通过文章来进行一个完整的学习,Code First是由先有代码后生成数据库:将通过一实例来进行学习:我们简单分为三层,其中DataLibrary为EF上下文处理层,Mo ...

  3. 20.2.翻译系列:EF 6中基于代码的数据库迁移技术【EF 6 Code-First系列】

    原文链接:https://www.entityframeworktutorial.net/code-first/code-based-migration-in-code-first.aspx EF 6 ...

  4. 20.翻译系列:Code-First中的数据库迁移技术【EF 6 Code-First系列】

    原文链接:https://www.entityframeworktutorial.net/code-first/migration-in-code-first.aspx EF 6 Code-First ...

  5. 14.翻译系列:从已经存在的数据库中生成上下文类和实体类【EF 6 Code-First系列】

    原文链接:https://www.entityframeworktutorial.net/code-first/code-first-from-existing-database.aspx EF 6 ...

  6. 5.翻译系列:EF 6中数据库的初始化(EF 6 Code-First 系列)

    原文地址:http://www.entityframeworktutorial.net/code-first/database-initialization-in-code-first.aspx EF ...

  7. 10.1.翻译系列:EF 6中的实体映射【EF 6 Code-First系列】

    原文链接:https://www.entityframeworktutorial.net/code-first/configure-entity-mappings-using-fluent-api.a ...

  8. 10.2.翻译系列:使用Fluent API进行属性映射【EF 6 Code-First】

    原文链接:https://www.entityframeworktutorial.net/code-first/configure-property-mappings-using-fluent-api ...

  9. 21.翻译系列:Entity Framework 6 Power Tools【EF 6 Code-First系列】

    原文链接:https://www.entityframeworktutorial.net/code-first/entity-framework-power-tools.aspx 大家好,这里就是EF ...

随机推荐

  1. HZAU 1205 Sequence Number(双指针)

    题目链接:http://acm.hzau.edu.cn/problem.php?id=1205 [题意]给你一串数,要求你找到两个数a[i],a[j],使得a[i]<=a[j]且j>=i且 ...

  2. 旺财C# .NET代码生成器之DTcms4/5代码批量生成功能

    经近半年的实战积累.于2017年6月底,增加对第三方开源软件DTcms(4和5都支持)的代码生成支持. 可以一键生成的DTcms4/5代码如下:1.Model经典三层实体2.DAL经典三层数据库访问层 ...

  3. 「2018山东一轮集训」 Tree

    为什么出题人这么毒瘤啊??!!一个分块还要带log的题非要出成n<=2*1e5....... 为了卡过最后两个点我做了无数常数优化,包括但不限于:把所有线段树改成 存差分的树状数组:把树剖求LC ...

  4. BZOJ 4247 挂饰(背包问题)

    [题目链接] http://www.lydsy.com/JudgeOnline/problem.php?id=4247 [题目大意] JOI君有N个装在手机上的挂饰,编号为1...N. JOI君可以将 ...

  5. linux中django部署

    下载nginx yum install nginx rpm -ql nginx systemctl start nginx /usr/share/nginx/html # html页面 /etc/ng ...

  6. BigInt的实现——C++编程风格读书笔记

    C++编程风格这本书前面一些章节都觉得很简明易懂,但是读到效率这一章是才充分认识到读别人的代码还是很痛苦的一件事.书中给出的需要改进的初始类如下: class BigInt { private: ch ...

  7. MYSQL复习笔记8-数据完整性

    Date: 20140207Auth: Jin 一.数据完整性的分类数据完整性是指数据库中数据在逻辑上的一致性和准确性.包括三种1.实体完整性又称行的完成性,要求表中有一个主键,其值不能为空且唯一地标 ...

  8. Linux下KVM的图形界面管理工具(WebVirtMgr)(Web版)

    WebVirtMgr面板 截图 介绍 WebVirtMgr是一个基于libvirt的Web界面,用于管理虚拟机.它允许您创建和配置新域,并调整域的资源分配.VNC查看器为来宾域提供完整的图形控制台.K ...

  9. NHibernate官方文档中文版-框架架构(Architecture)

    总体概览 一个非常高层次的NHibernate架构: 这个图展示了NHibernate使用数据库和配置信息来为应用程序提供持久化服务(和持久化对象). 我们想展示一个更加详细的运行时架构.但是NHib ...

  10. 安装maven,eclipse及eclipse配置maven

    现在的eclipse,maven安装非常简单.下载解压就可以用. 官网上下载eclipse, https://www.eclipse.org/downloads/eclipse-packages/ 选 ...