【问题标题】:Do not create existing table during Migration迁移期间不要创建现有表
【发布时间】:2015-08-11 17:56:24
【问题描述】:

我正在使用实体通过代码优先迁移连接到现有数据库。在数据库中,我需要连接到一些已经存在的表并添加一些新表。我以为我已经弄清楚了,但它仍在尝试创建已经存在的表。这是其中一张表的模型:

namespace PTEManager.Domain
{
    public partial class OpsUser
    {
        public int u_user_id { get; set; }

        public Guid DepartmentID { get; set; }

        public string email_addr { get; set; }

        public string first_nme { get; set; }

        public string last_nme { get; set; }

        public Guid msrepl_tran_version { get; set; }

        public string status { get; set; }

        public string user_nme { get; set; }

        public int u_branch_id { get; set; }

    }
}

这是我将该模型映射到表格的地方:

namespace PTEManager.Domain.Mapping
{
    class UserMap : EntityTypeConfiguration<OpsUser>
    {
        public UserMap()
        {
            // Primary Key
            this.HasKey(t => t.u_user_id);

            // Properties
            this.Property(t => t.DepartmentID);

            this.Property(t => t.email_addr)
                .IsRequired()
                .HasMaxLength(50);

            this.Property(t => t.first_nme)
                .IsRequired()
                .HasMaxLength(30);

            this.Property(t => t.last_nme)
                .IsRequired()
                .HasMaxLength(30);

            this.Property(t => t.msrepl_tran_version)
                .IsRequired();

            this.Property(t => t.status)
                .IsRequired()
                .HasMaxLength(1);

            this.Property(t => t.user_nme)
                .IsRequired()
                .HasMaxLength(15);

            this.Property(t => t.u_branch_id)
                .IsRequired();

            // Table & Column Mappings
            this.ToTable("Users");
            this.Property(t => t.u_user_id).HasColumnName("u_user_id");
            this.Property(t => t.DepartmentID).HasColumnName("DepartmentID");
            this.Property(t => t.email_addr).HasColumnName("email_addr");
            this.Property(t => t.first_nme).HasColumnName("first_nme");
            this.Property(t => t.last_nme).HasColumnName("last_nme");
            this.Property(t => t.msrepl_tran_version).HasColumnName("msrepl_tran_version");
            this.Property(t => t.status).HasColumnName("status");
            this.Property(t => t.user_nme).HasColumnName("user_nme");
            this.Property(t => t.u_branch_id).HasColumnName("u_branch_id");
        }
    }
}

这是我的 dbContext:

namespace PTEManager.Domain.Data
{
    public class DataContext : DbContext, IDataContext
    {
        static DataContext()
        {
            Database.SetInitializer<DataContext>(null);
        }

        public DataContext()
            : base("OPSPROD")
        {
        }


        /// 
        public DbSet<OpsUser> OpsUsers { get; set; }

        public DbSet<Package> Packages { get; set; }

        public DbSet<PTEInteractiveCourse> PTEInteractiveCourses { get; set; }

        public DbSet<PTETrackingClass> PTETrackingClasses { get; set; }

        public DbSet<STCIProductInteractiveInfo> STCIProductInteractiveInfos { get; set; }

        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {

            modelBuilder.Configurations.Add(new UserMap());
            modelBuilder.Configurations.Add(new PackageMap());
            modelBuilder.Configurations.Add(new STCIProductInteractiveInfoMap());
        }
    }

}

但是,当我添加一个新的迁移时,它仍然会创建这个:

CreateTable(
                "dbo.Users",
                c => new
                    {
                        u_user_id = c.Int(nullable: false, identity: true),
                        DepartmentID = c.Guid(nullable: false),
                        email_addr = c.String(nullable: false, maxLength: 50),
                        first_nme = c.String(nullable: false, maxLength: 30),
                        last_nme = c.String(nullable: false, maxLength: 30),
                        msrepl_tran_version = c.Guid(nullable: false),
                        status = c.String(nullable: false, maxLength: 1),
                        user_nme = c.String(nullable: false, maxLength: 15),
                        u_branch_id = c.Int(nullable: false),
                    })
                .PrimaryKey(t => t.u_user_id);

只是为了确保我尝试运行 update-database 并且它会告诉我

数据库中已经有一个名为“用户”的对象。

这是我找到有关映射到现有表的信息的地方:

http://www.codeproject.com/Tips/661053/Entity-Framework-Code-First-Map

如何防止它尝试创建现有表并仅映射到它?

【问题讨论】:

  • 您在哪里将UserMap 配置添加到“DbModelBuilder”?
  • @T.Rahgooy,对不起,我忘了添加我的 datacontext 类 - 我现在将它添加到原始问题中。
  • 如果现有表具有您想要的确切属性,只需注释创建表并应用迁移。
  • @T.Rahgooy 现在它说:“列 'dbo.Users.u_user_id' 与在外键 'FK_dbo.PTEInteractiveCourses_dbo.Users_ModifyUserId' 中引用列 'PTEInteractiveCourses.ModifyUserId' 的数据类型不同. 无法创建约束。"
  • PTEInteractiveCourses 中引用该表的外键ModifyUserIdint吗?

标签: c# asp.net-mvc entity-framework model entity-framework-migrations


【解决方案1】:

这是实体框架本身的限制,您无法解决。为了使迁移正常运行,他们必须了解您的整个数据库架构,这意味着他们必须对您的整个数据库架构负责。您不能迁移部分实体而不迁移其他实体。

如果您有一个需要使用现有表的用例,那么您应该将它们移至单独的数据库并使用两个上下文:一个用于 Entity Framework 负责的实体,它将被迁移到,一种只是连接到您现有的数据库,并且禁用了迁移。

从技术上讲,我认为您可以在两种情况下使用相同的数据库,只要您正确隔离实体即可。然而,问题就在这里:当它们在同一个数据库中时,尝试关联实体(外键)太诱人了。如果您在迁移上下文中的实体与非迁移上下文中的实体之间创建关系,则迁移上下文实际上也将假定该实体的所有权,并尝试创建表。然后,你又回到了同一条船上。通过为两个不同的上下文使用两个单独的数据库,您可以放心,不会出现溢出。

【讨论】:

  • 我需要将不同的模型放入不同的解决方案中吗?
  • 没有。只是不要在迁移上下文中为不应迁移的实体添加 DbSet。正如我在上面的编辑中解释的那样,您还需要注意不要在两个不同的上下文中创建实体之间的关系,因为即使没有明确的 DbSet,任何与具有 DbSet 的实体相关的实体都将被跟踪同样的上下文。
猜你喜欢
  • 2018-05-22
  • 2015-04-25
  • 2020-04-18
  • 2021-08-23
  • 2021-09-01
  • 2023-01-06
  • 2015-03-28
  • 2022-01-17
相关资源
最近更新 更多