• 第十六节: EF的CodeFirst模式通过Fluent API修改默认协定


    一. 简介

     1. 优先级:Fluent API > data annotations > default conventions.

     2. 所有的Fluent API配置都要在 OnModelCreating这个重写方法中进行

     3. 常见的配置:

       ① 获取表对应的配置根: var stu =modelBuilder.Entity<XXX>();

       ② 设置主键:HasKey<string>(s => s.studentKey);

       ③ 获取属性:stu.Property(p => p.stuName)

       ④ 设置可空或非空:IsRequired和IsOptional

       ⑤ 设置最大值:HasMaxLength

       ⑥ 修改属性名→修改属性的次序→修改属性对应的数据库类型:HasColumnName→HasColumnOrder→HasColumnType

       ⑦ 修改表名:ToTable

     4. 可以建立多个Fluent API的配置文件,然后通过 modelBuilder.Configurations.Add(new XXX());添加到一起

    PS:或者利用这句话   modelBuilder.Configurations.AddFromAssembly(Assembly.GetExecutingAssembly());     把所有的配置文件一次性全部加进来

    二. 代码实战

     1   public class Student5
     2     {
     3         //主键声明
     4         public string studentKey { get; set; }
     5 
     6         //非空声明
     7         public string stuName { get; set; }
     8 
     9         //最大长度
    10         public string stuTxt1 { get; set; }
    11 
    12         //最大长度和最小长度
    13         public string stuTxt2 { get; set; }
    14 
    15         //设置为时间戳
    16         public byte[] rowVersion { get; set; }
    17 
    18         //并发检查
    19         public string stuTxt3 { get; set; }
    20 
    21         //public virtual StudentAddress5 stuAddress5 { get; set; }
    22     }
    23    public class StudentAddress5
    24     {
    25          //既是主键、又是外键
    26         public string stuAddressId { get; set; }
    27 
    28          //设置映射数据库中表的列名
    29         public string stuAddressName { get; set; }
    30 
    31         //设置映射数据库中表的列名、顺序、类型
    32         public string stuAddrssName2 { get; set; }
    33 
    34         //不映射数据
    35         public string addressNum { get; set; }
    36 
    37         //不映射数据
    38         public string txt1 { get { return stuAddrssName2; } }
    39 
    40         //不映射数据
    41         public string _txt2 = "1";
    42         public string txt2 { set { _txt2 = value; } }
    43 
    44         //public virtual Student5 stu { get; set; }
    45     }
    46 
    47     /// <summary>
    48     /// Game实体,与其它两个没有什么直接关系,单纯的为了演示, Fluent API的配置,可以根据实体进行拆分
    49     /// 文件来配置,方便管理
    50     /// </summary>
    51     public class Game
    52     {
    53         public int GameId { get; set; }
    54 
    55         public string GameName { get; set; }
    56     }
     1      /// <summary>
     2     /// Game实体的配置文件
     3     /// </summary>
     4     public class GameConfiguration : EntityTypeConfiguration<Game>
     5     {
     6         public GameConfiguration()
     7         {
     8             this.HasKey(p => p.GameId);
     9 
    10             this.Property(p => p.GameName).HasMaxLength(10).IsRequired();
    11         }
    12     }
     1 public class dbContext5 : DbContext
     2     {
     3         public dbContext5()
     4             : base("name=dbContext5")
     5         {
     6 
     7         }
     8 
     9         public DbSet<Student5> Student5 { get; set; }
    10 
    11         public DbSet<StudentAddress5> StudentAddress5 { get; set; }
    12 
    13 
    14         protected override void OnModelCreating(DbModelBuilder modelBuilder)
    15         {
    16             //所有的FluentAPI均在方法中进行重写
    17 
    18             //一. 属性层次上的设置
    19             var stu = modelBuilder.Entity<Student5>();
    20             var stuAddress = modelBuilder.Entity<StudentAddress5>();
    21 
    22             //1. 设置主键 
    23             stu.HasKey<string>(s => s.studentKey);
    24             stuAddress.HasKey<string>(s => s.stuAddressId);   //为什么需要动态设置主键,有待研究??
    25 
    26             //2. 设置非空   (扩展:IsOptional 设置可空)
    27             stu.Property(p => p.stuName).IsRequired();
    28 
    29             //3. 设置最大值(不能设置最小值)
    30             stu.Property(p => p.stuTxt1).HasMaxLength(10);
    31 
    32 
    33             //4. 修改列的名称、排序、类型
    34             stuAddress.Property(p => p.stuAddrssName2).HasColumnName("myAddress2").HasColumnOrder(1).HasColumnType("varchar");
    35 
    36             //5.修改表名
    37             stu.Map<Student5>(c =>
    38             {
    39                 c.ToTable("MyStudent");
    40 
    41             });
    42 
    43             //6.将一个实体映射成多张表,并分别给其命名
    44             //stuAddress.Map<StudentAddress5>(c =>
    45             //{
    46             //    c.Properties(p => new
    47             //    {
    48             //        p.stuAddressId,
    49             //        p.stuAddressName
    50             //    });
    51             //    c.ToTable("MyStuAddress1");
    52             //}).Map<StudentAddress5>(c =>
    53             //{
    54             //    c.Properties(p => new
    55             //    {
    56             //        p.stuAddressId,
    57             //        p.stuAddrssName2
    58             //    });
    59             //    c.ToTable("MyStuAddress2");
    60             //});
    61 
    62 
    63 
    64 
    65             //三. 将Game实体的配置添加进来
    66             modelBuilder.Configurations.Add(new GameConfiguration());
    67 
    68             base.OnModelCreating(modelBuilder);
    69         }
    70     }
    1    <!--正宗的CodeFirst Fluent API-->
    2     <add name="dbContext5" connectionString="data source=localhost;initial catalog=CodeFirstDB5;persist security info=True;user id=sa;password=123456;MultipleActiveResultSets=True;App=EntityFramework" providerName="System.Data.SqlClient" />
    3    

    三. 总结

       无论是DataAnnotation还是Fluent API,都会发现一个现象,当数据库结构发生变化的时候,就会抛出异常,不得不把数据库删除,重新生成,这样就会导致原数据库中的数据丢失,在实际开发中,显然是不可取的。那么为什么会抛异常呢?怎么解决这个数据丢失的问题呢?详见下一个章节:数据库初始化策略和数据迁移。

     

    !

    • 作       者 : Yaopengfei(姚鹏飞)
    • 博客地址 : http://www.cnblogs.com/yaopengfei/
    • 声     明1 : 本人才疏学浅,用郭德纲的话说“我是一个小学生”,如有错误,欢迎讨论,请勿谩骂^_^。
    • 声     明2 : 原创博客请在转载时保留原文链接或在文章开头加上本人博客地址,否则保留追究法律责任的权利。
     
  • 相关阅读:
    Windows Phone 31 日谈——第18日:WebBrowser控件
    Windows Phone 31 日谈——第19日:推送通知
    使用bat文件启动服务
    绝代反向指标——丘吉尔 炒股第二天就崩盘
    插入数据库返回自增长序号
    大并发服务器开发
    在这个不相信爱情的时代里,巴菲特的故事似乎让我又相信爱情了
    mysql操作语句
    马云三历高考才进大学 第一次高考数学考1分
    俞敏洪的屌丝逆袭 大学考了三次进北大
  • 原文地址:https://www.cnblogs.com/yaopengfei/p/7816179.html
Copyright © 2020-2023  润新知