以下是EF中Data Annotation和 Fluenlt API的不同属性约定的对照。
 
Length
Data Annotation
MinLength(nn)
MaxLength(nn)
StringLength(nn)
Fluent
Entity<T>.Property(t=>t.PropertyName).HasMaxLength(nn)

在SQL Server中,string会转换为nvarchar(max),bit会转换为varbinary(max) 如果是SQL CE这里的最大值会变成4000(毕竟人家是嵌入式数据库). 通过MinLength等来限制字段在数据库中的长度。MinLength和MaxLength会受到EntityFramework的验证,不会影响到数据库。

[StringLength(,MinimumLength= )]
public string Description { get; set; }

Data Type

Data Annotation
Column(TypeName=“xxx”)
Fluent
Entity<T>.Property(t=>t.PropertyName)
.HasColumnType (“xxx”)
  [Column(TypeName = "image")]
public byte[] Photo { get; set; }

Nullability

Data Annotation
Required
Fluent
Entity<T>.Property(t=>t.PropertyName).IsRequired
  [Required]
public string Name { get; set; }

Keys

Data Annotation
Key
Fluent
Entity<T>.HasKey(t=>t.PropertyName)

EF需要每个实体必须拥有一个Key,context会根据key来跟踪对象。而且默认是自动递增的。

Database-Generated

Data Annotation
DatabaseGenerated(DatabaseGeneratedOption)
Fluent
Entity<T>.Property(t=>t.PropertyName)
.HasDatabaseGeneratedOption(DatabaseGeneratedOption)
 
 
 
  [Key]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
public int DestinationId { get; set; }
DatabaseGeneratedOption 为None可以关闭自动增加。

TimeStampRowVersion
Data Annotation
TimeStamp
Fluent
Entity<T>.Property(t=>t.PropertyName).IsRowVersion()

timestamp和rowversion是同一个数据类型的不同叫法,不同的数据库显示不同

[Timestamp]
public byte[] RowVersion { get; set; }

时间戳:数据库中自动生成的唯一二进制数字,与时间和日期无关的, 通常用作给表行加版本戳的机制,当行数据发生修改,时间戳会自动增加。存储大小为 8个字节。一个表只有一个时间戳列,不适合做主键,因为其本身是变化的。

在控制并发时起到作用:
    用户A/B同时打开某条记录开始编辑,保存是可以判断时间戳,因为记录每次被更新时,系统都会自动维护时间戳,所以如果保存时发现取出来的时间戳与数据库中的时间戳如果不相等,说明在这个过程中记录被更新过,这样的话可以防止别人的更新被覆盖.

Non-Timestamp for Concurrency

Data Annotation
ConcurrencyCheck
Fluent
Entity<T>.Property(t=>t.PropertyName).IsConcurrencyToken()

对于那些没有时间戳的数据库中也提供并发检查。避免造成同时修改造成的冲突。和上面的Timestamp一样,当模型发生改变写入到数据库的时候,数据库不但通过key找到了这一行数据,还会比对标记了Concurrency字段的值是否是原来的值。

public class Person
{
public int PersonId { get; set; }
[ConcurrencyCheck]
public int SocialSecurityNumber { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
} //....
private static void UpdatePerson()
{
using (var context = new BreakAwayContext())
{
var person = context.People.FirstOrDefault();
person.FirstName = "Rowena";
context.SaveChanges();
}
}

SQL:

exec sp_executesql N'update [dbo].[People]
set [FirstName] = @0
where (([PersonId] = @1) and ([SocialSecurityNumber] = @2))
',N'@0 nvarchar(max) ,@1 int,@2 int',@0=N'Rowena',@1=1,@2=12345678

Non-Unicode Database Types

Data Annotation
unavailable
Fluent
Entity<T>.Property(t=>t.PropertyName).IsUnicode(boolean)
Property(l => l.Owner).IsUnicode(false);

默认情况下,所以string都会映射成数据库中的Unicode类型。data Annotation 不支持。

Precision and Scale of Decimals

精度定义:

Data Annotation
unavailable
Fluent
Entity<T>.Property(t=>t.PropertyName).HasPrecision(n,n)
Property(l => l.MilesFromNearestAirport).HasPrecision(, );

上面表示MilesFromNearestAirport是八位数,保留一位小数。data Annotation 不支持。

complex type

Complex Type需要满足3个条件:1.没有key(Id),2.complex类型只能包含原始属性(primitive properties),3.当它用到别的类中时,只能是非集合(non-collection)形式。

下面的Address就是一个complex type

public class Address
{
//public int AddressId { get; set; }
public string StreetAddress { get; set; }
public string City { get; set; }
public string State { get; set; }
public string ZipCode { get; set; }
}
public class Person
{
public int PersonId { get; set; }
public int SocialSecurityNumber { get; set; }
public string FirstName { get; set; }
public string LastName { get; set; }
public Address Address { get; set; }
}

生成的表如下。

没有创建Address表,而是作为列出现在了people表中,并注意这些列的命名方式。如果想保留AddressId且还是ComplexType  可以这样。
[ComplexType]
public class Address
{
public int AddressId { get; set; }
public string StreetAddress { get; set; }
public string City { get; set; }
public string State { get; set; }
public string ZipCode { get; set; }
}

Api :

modelBuilder.ComplexType<Address>().Property(p => p.StreetAddress).HasMaxLength();

More Complicated Complex Types

即 nested complex type. 内嵌复合类型
 
public class PersonalInfo
{
public Measurement Weight { get; set; }
public Measurement Height { get; set; }
public string DietryRestrictions { get; set; }
}
public class Measurement
{
public decimal Reading { get; set; }
public string Units { get; set; }
} public PersonalInfo Info { get; set; }

Person包含PersonInfo,PersonInfo包含两个Measurement。先在构造函数中初始化:

public Person()
{
Address = new Address();
Info = new PersonalInfo
{
Weight = new Measurement(),
Height = new Measurement()
};
}

这时运行会报错,说PersonInfo 没有定义主键。因为他包含的两个Measurement不是原始类型(primitive types)。

需要给PersonInfo加上 ComplexType,再次运行生成的表如下:
 
 
对于Complex类型使用Api的方式,如果要把配置类单独出来 需要继承ComplexTypeConfiguration  而不是EntityTypeConfiguration
public class AddressConfiguration :
ComplexTypeConfiguration<Address>
{
public AddressConfiguration()
{
Property(a => a.StreetAddress).HasMaxLength();
}
}

再在OnModelCreating方法中加入

modelBuilder.Configurations.Add(new AddressConfiguration());
 
 

Programming Entity Framework CodeFirst -- 约定和属性配置的更多相关文章

  1. 【读书笔记】Programming Entity Framework CodeFirst -- 初步认识

    以下是书<Programming Entity Framework Code First>的学习整理,主要是一个整体梳理. 一.模型属性映射约定 1.通过 System.Component ...

  2. Entity Framework 系统约定配置

    前言 Code First之所以能够让开发人员以一种更加高效.灵活的方式进行数据操作有一个重要的原因在于它的约定配置.现在软件开发越来越复杂,大家都试图将软件设计的越来越灵活,很多内容我们都希望是可配 ...

  3. Entity Framework Codefirst的配置步骤

    Entity Framework Codefirst的配置步骤: (1) 安装命令: install-package entityframework (2) 创建实体类,注意virtual关键字在导航 ...

  4. 第三篇:Entity Framework CodeFirst & Model 映射 续篇 EntityFramework Power Tools 工具使用

    上一篇 第二篇:Entity Framework CodeFirst & Model 映射 主要介绍以Fluent API来实作EntityFramework CodeFirst,得到了大家一 ...

  5. 第二篇:Entity Framework CodeFirst & Model 映射

    前一篇 第一篇:Entity Framework 简介 我有讲到,ORM 最关键的 Mapping,也提到了最早实现Mapping的技术,就是 特性 + 反射,那Entity Framework 实现 ...

  6. Entity Framework CodeFirst数据迁移

    前言 紧接着前面一篇博文Entity Framework CodeFirst尝试. 我们知道无论是“Database First”还是“Model First”当模型发生改变了都可以通过Visual ...

  7. [Programming Entity Framework] 第3章 查询实体数据模型(EDM)(一)

    http://www.cnblogs.com/sansi/archive/2012/10/18/2729337.html Programming Entity Framework 第二版翻译索引 你可 ...

  8. entity framework codefirst 用户代码未处理DataException,InnerException基础提供程序在open上失败,数据库生成失败

    警告:这是一个入门级日志,如果你很了解CodeFirst,那请绕道 背景:这篇日志记录我使用Entity FrameWork CodeFirst时出现的错误和解决问题的过程,虽然有点曲折……勿喷 备注 ...

  9. ADO.NET Entity Framework CodeFirst 如何输出日志(EF 5.0)

    ADO.NET Entity Framework CodeFirst 如何输出日志(EF4.3) 用的EFProviderWrappers ,这个组件好久没有更新了,对于SQL执行日志的解决方案的需求 ...

随机推荐

  1. 设置secureCRT支持中文

    将options菜单下面的session options 中的 appearance 标签页里面的 character encoding 选择UTF-8就可以.

  2. linux下安装oracle

    一>1.关闭防火墙,禁用selinux vi /etc/selinux/config  修改SELINUX=disabled,然后重启,如果不想重启使用命令setenforce 0 2.安装依赖 ...

  3. Django-安装篇

    前提准备:Python,PIP Python直接去官网下载并安装:https://www.python.org/download/,本机安装Python版本:Python 2.7.10 PIP:htt ...

  4. 读书笔记之深入理解Nginx:模块开发与结构解析

    前言 我现在看书一般都是看自己能看懂的地方,看不懂就先略过,回头再看,下面就写自己看得懂的地方吧,并且把自己的理解也放到里面. 第一部分 Nginx能帮我们做什么 编译安装各个命令解释 configu ...

  5. 网页Email抓取 java

    import java.io.BufferedReader; import java.io.FileNotFoundException; import java.io.FileReader; impo ...

  6. maven pox配置

    Maven教程初级篇02:pom.xml配置初步 1. 创建项目并更改项目基本配置信息 在命令行下运行如下命令创建一个项目: 1 mvn archetype:create -DgroupId=net. ...

  7. PHP中实现MySQL嵌套事务的两种解决方案

    PHP中实现MySQL嵌套事务的两种解决方案 一.问题起源 在MySQL的官方文档中有明确的说明不支持嵌套事务: Transactions cannot be nested. This is a co ...

  8. 本地推送UILocalNotification

    //本地推送---无需网络,由本地发起 UILocalNotification *localNotification = [[UILocalNotification alloc]init]; //设置 ...

  9. C#的linq在winform中简单应用

    一.创建窗体应用程序 二.在窗体应用程序中添加linqtosql类,并且连接到sql server数据库中去 三.在资源管理器里打开数据表拖入linqtosql的视图中,并自己设置主键,并将同步设置为 ...

  10. Mac 下 WebStorm 配置go语言开发环境

    一.下载安装WebStorm,我的是 二.在WebStorm 中安装go插件 三.在本机安装go开发环境,直接装pkg文件,https://golang.org/doc/install 四.在WebS ...