zoukankan      html  css  js  c++  java
  • 如何将EFCore迁移分离到单独类库项目?

         上篇文章: EFCore生产环境数据库升级方案 中我们聊了如何将EFCore迁移(实体模型变更)应用到生产环境的方案,在上次的演示中,我们是将所有迁移存放到了定义DbContext的类库项目中去,在这边文章中我来介绍下如何将迁移单独存放到一个类库项目中去,以便管理EF生成的迁移文件。

    这篇文章中,我们继续使用 EFCore生产环境数据库升级方案 中的例子项目进行改造,来实现将所有EF迁移文件单独提取到类库项目中去,本文和 EFCore生产环境数据库升级方案 是同一个系列的文章,如果你还没有阅读前一篇文章,强烈建议先阅读前文。

    一、新建类库项目,将EF迁移文件及迁移快照文件移动到新的类库项目中

    新建名称为 EFMigrations.DataMigrations 的类库项目

    这里需要注意的是:如果还没有生成任何迁移文件,则请先至少生成一个,再将新生成的迁移文件复制到新建的类库项目EFMigrations.DataMigrations 中去。

    二、类库项目添加对包含DbContext上下文类的引用。

    添加EFMigrations.Models类库项目的引用到EFMigrations.DataMigrations,如下:

     

    三、将默认的迁移程序集指定为新建的类库项目。

    将EFMigrations.Models 中的所有的EF迁移文件及迁移生成的SQL脚本文件移动到EFMigrations.DataMigrations项目中去。

    移动完毕后,EFMigrations.Models中仅包含EF DbContext 上下文类,以及实体模型,如下图所示:

    四、告诉启动项目迁移程序集是哪个

    启动项目指的是告诉 EF命令行迁移工具从哪个项目开始启动,然后执行迁移文件的生成,这里我们的启动项目是EFMigrations.Web 项目,修改Startup.cs文件中的ConfigureService方法如下:

            public void ConfigureServices(IServiceCollection services)
            {
                services.AddDbContext<MyDbContext>(builder=> {
                    builder.UseSqlServer(Configuration["ConnectionStrings:ConnectionStr"],optionsBuilder=> {
                        //这里告诉EFcore 命令行迁移工具,等下生成的迁移文件放到EFMigrations.DataMigrations 项目中去。
                        optionsBuilder.MigrationsAssembly("EFMigrations.DataMigrations");
                    });
                });
                services.AddControllersWithViews();
            }

    添加EFMigrations.DataMigrations的引用到EFMigrations.Web,然后重新生成下EFMigrations.Web项目,否则等下生成迁移会失败,因为不添加引用等下EFMigrations.Web项目启动后开始生成迁移的时候会找不到EFMigrations.DataMigrations.dll

    五、测试新添加的迁移是否正常生成到了新建的类库项目中去。

    我们新建一个实体模型OrderInfo,并将其添加到DbContext 上下文中去。

    using System;
    using System.Collections.Generic;
    using System.ComponentModel.DataAnnotations;
    using System.ComponentModel.DataAnnotations.Schema;
    using System.Text;
    
    namespace EFMigrations.Models
    {
        public class OrderInfo
        {
            [Key]
            [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
            public int OrderId { get; set; }
            public int ProductId { get; set; }
            public double Price { get; set; }
            public int BuyCount { get; set; }
            public int UserId { get; set; }
        }
    }
    

    修改DbContext上下文类,增加OrderInfo实体映射。

    using Microsoft.EntityFrameworkCore;
    using System;
    using System.Collections.Generic;
    using System.Text;
    
    namespace EFMigrations.Models
    {
        public class MyDbContext : DbContext
        {
            /// <summary>
            /// 这里一定要声明一个接收DbContextOptions参数的构造函数,否则无法正常添加迁移。
            /// </summary>
            /// <param name="options"></param>
            public MyDbContext(DbContextOptions<MyDbContext> options) : base(options)
            {
            }
            public DbSet<UserInfo> UserInfos { get; set; }
            public DbSet<OrderInfo> OrderInfos { get; set; }
            protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
            {
                base.OnConfiguring(optionsBuilder);
            }
        }
    }

    打开程序包管理控制台,输入以下命令:

    cd ./EFMigrations.DataMigrations  将当前目录定位到迁移程序所在项目的根目录下,免得下面这个步骤生成迁移文件的时候还要额外用-p 参数指定迁移程序集的项目路径。

    dotnet ef migrations add OrderInfo_CreateTable -s ../EFMigrations.Web 

    迁移生成成功后如下:

    将新生成的迁移转换成SQL,在程序包管理控制台中输入以下命令:

    dotnet ef migrations script 20210830142733_UserInfo_AddColumns 20210902141104_OrderInfo_CreateTable -s ../EFMigrations.Web -o ./SqlScripts/OrderInfo_CreateTable.sql

    以上命令的意思是将 20210830142733_UserInfo_AddColumns迁移(不包含)的下一个迁移开始,截止到 20210902141104_OrderInfo_CreateTable(包含) 之间的所有迁移转换成SQL脚本进行生成,生成成功后,SQL脚本如下:

    六、将SQL脚本升级到数据库

    • 首先需要将生成的SQL脚本设置成在生成项目的时候嵌入到程序集:鼠标右击 OrderInfo_CreateTable.sql ,选择属性->生成操作->嵌入的资源
    • 然后将EFMigrations.Models 类中的 ApplicationBuilderExtensions 类移动到EFMigrations.DataMigrations项目中去,之所以这么做是方便dbup-sql 类库找.sql脚本时直接从当前程序集中查找

           

    • 重启网站,看下是否新SQL脚本是否成功被升级到了数据库

    这里需要注意的是,由于在上一篇文章中我已经将前面两个SQL 脚本升级到了数据库中,并且很有意思的事情是dbup-sqlserver记录已升级脚本的名称时带上了程序集明明空间,因此这里直接运行会升级失败,我们必须手动先将数据库中的已升级脚本记录的前缀名称更新为EFMigartions.DataMigrations开头方能再次升级成功。

    我们将EFMigrations.Models替换成EFMigrations.DataMigrations后再重新升级,如下图显示,表示升级成功了

    337901356
  • 相关阅读:
    跳出iframe
    leetcode 225. Implement Stack using Queues
    leetcode 206. Reverse Linked List
    leetcode 205. Isomorphic Strings
    leetcode 203. Remove Linked List Elements
    leetcode 198. House Robber
    leetcode 190. Reverse Bits
    leetcode leetcode 783. Minimum Distance Between BST Nodes
    leetcode 202. Happy Number
    leetcode 389. Find the Difference
  • 原文地址:https://www.cnblogs.com/chenxinblogs/p/15221151.html
Copyright © 2011-2022 走看看