2

DbMigrator を使用して移行を実行する際に問題が発生しました。どういうわけか、移行クラスが実行されず、もちろんデータベースに反映されません。

私が実装しようとしているのは、移行をバージョンにグループ化することです。基本的に、すべてのバージョンの派生元である Version 基本クラスがあります。

たとえば、バージョン 1.0.0.0 に対応するクラス Version1000 があります。

バージョン クラスには、対応するバージョンに関連する移行の実行を担当する ExecuteMigrations というメソッドがあります。

バージョン クラス (1.0.0.0 の場合は Version1000) のサンプルを次に示します。DbMigrator を使用した ExecuteMigrations メソッドを参照してください。また、DbMigrationsConfiguration から派生した VersionConfiguration クラスも使用しています。名前空間、ディレクトリ、ContextType を設定する場所にあります。等..

public class Version1000 : Version
{
    public override string VersionNumber
    {
        get { return "1.0.0.0"; }
    } 

    public static Version Version
    {
        get
        {
            return new Version1000();
        }
    }

    public override void ExecuteMigrations()
    {
        var configuration = new VersionConfiguration();
        configuration.TargetDatabase = new DbConnectionInfo(MyCustomContext.CONTEXT_CONNECTION_STRING_NAME);
        var migrator = new DbMigrator(configuration);
        migrator.Update();
    }
}

VersionConfiguration クラス

class VersionConfiguration : DbMigrationsConfiguration<MyCustomContext>
{
    public VersionConfiguration()
    {
        AutomaticMigrationsEnabled = false;
        MigrationsNamespace = "Some.Namespace._1000";
        MigrationsDirectory = "Migration\\1000";
        ContextType = typeof(MyCustomContext);
    }

    protected override void Seed(MyCustomContext context)
    {
        base.Seed(context);
    }
}

アプリケーションのアプリケーション開始時に、データベースの現在のバージョンを確認し、現在のデータベースに適用されていないバージョンを適用します。これは、バージョン クラスの ExecuteMigrations メソッドを呼び出すことによって行われます。

DbMigrator.Update メソッドが呼び出されたときに変更がデータベースに反映されず、DbMigrationsConfiguration で設定されたフォルダー/名前空間内の移行クラスが実行されないという例外はありません。

アプリケーションの種類: ASP.NET MVC 4 .NET Framework: 4.5

4

2 に答える 2

1

移行では IVersionMetadata も実装する必要があり、Id、Source、および Target プロパティを提供する必要があります。次のような値が必要です。

Id = string.Format("{0}_{1}", SomeSequenceNumber.ToString().PadLeft(15, '0'), "Name")
Source = null
Target = "H4sIAAAAAAAEAL1Y23LbNhB970z/gYOn9iGCJEdJ66GSsWW78bSyO6aT1wxErmRMcGEJ0BX7a33oJ/UXuryKF11o2e6bCKx2z1lwD47079//uB/XUjiPEBmu1ZSMBkPigPJ1wNVqSmK7fPMT+fjh++/cy0CunS9l3Ekah99UZkoerA1PKTX+A0hmBpL7kTZ6aQe+lpQFmo6Hw5/paEQBUxDM5TjuXawsl5A94ONMKx9CGzMx1wEIU6zjjpdldW6YBBMyH6Zknpzzv4hzJjjD4h6IJXHCt6efDXg20mrlhcxyJu6TEHB/yYSBAupp+LYv2uE4RUuZUtpiOq2OYksqHsjkEhnbBJlaxhVEGaUpORdMfUsXYW3r4dUXPLBF6CdurI4S4uQbKcGc/6DYudN/Yiven14bLzEW5JTYKN6Qf98L/GhMR8OMvOSrKONuiEPrTGiLSpdliq2JOsf2bhe2d8djazbtV0i2lGnEYNTvkQ4hsskdLAuY8zLhdbAVJz2cojhFRNAjg0sxrrlSZtyGqDhsG+FYEmfO1r+BWtmHKRlPJsS54msIypXijf+sOE4xlNVvYiHYQkC1fxhhC0+d3k44k9H4f4KTCUWJ5Jwrlk5GDQl+3I7k+aXxMYh9W4jhnm6cvE4zygFM626UkuZSWUoq3aGp7pyFIQKtaWyx4ni5wM7eeE9XO5nnoL7ZJ3pVJZQEtoLWbvqOBXDFI2MvmGULlvZiFshOWB/RLEu1tPP1JaghgiWK9HOOJK89SAkO8rhBNemmVPLBftVs1dsc4RV2VYKyWYOh6sUhFe7kyy5eJli0T5NmWsRSHSefu0vUZaZe4UnqupdDLhwN9PnSs9K2RaGev73Xq5BLW4fafsto5zVr3TDtWdh3h7dDquqVnrR0wy1m+LBh6wx1HkIcbMsjD9KBrg+F94eYCY58NwFzpvgSjL3X3wDNZzqFLQN4hDmjxgSih0PralIvm5aN2l6nlrdhSoKFxjskvwC+fq0m6XUl66Uc3WQXtsmLOrpOmac6ui7Opzq6QxmOcnTqkUX+A4u6nq5rCg4COGjYtlbLLNvzqzX8GNZZZJbsB8nWP75E+u2eayuhkyP49LNUXclzaf2XrHsBhq8285P+rlXgp0e+SVrGXKulLkmietTBlCHtFoNlAYrQWWT5kvkWt30wJnOdX5iIMeRSLiC4VrexDWN7ZgzIhUjqVF26v37mG5uY3dswm8uXoIAwOVKAW3UecxFUuK/yU6I9UqR6/AvgejZK6Lox3SqpMt1o1TNR0b4LCEEFeN/cgwwFJjO3ymOPsBvb4R42O+ZecIaTL02RY/P99I8Vmv6z8uE/KRLfnIsRAAA=";

おそらく、Target パラメーターに関するいくつかの明確化: モデル全体の圧縮バージョンが含まれています。彼らは EF でターゲットを指定する必要性を取り除きたいと考えていますが、EF6 alpha3 でもこれが必要です。上記の文字列は、空のモデルの圧縮形式です。それを定数として置くだけで、魅力的に機能します...

また: 私のプロジェクトでは、間違った Id 形式があり、何もしませんでした。EFソースでそれについてすぐにもっと知る必要がありますが、今のところ、これがあなたのケースに役立つかもしれません!

于 2013-04-26T14:53:15.160 に答える
-1

うーん、あなたのコードは非常に奇妙に見えます。エンティティ クラスまたはそれらへの参照はどこにありますか? バージョン 1.0.0.0 にはどのようなエンティティ/データベース オブジェクトが含まれていますか?

コードが最初に言うように、エンティティを記述する必要があります。

using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;

namespace StartReg.Data {        
    public class UserSession {
        [Key]
        [DatabaseGenerated(DatabaseGeneratedOption.Identity)]
        public int UserSessionId { get; set; }

        [Required]
        [MaxLength(100)]
        public string UserId { get; set; }

        [ForeignKey("UserId")]
        public virtual User User { get; set; }

        [Required]
        public DateTimeOffset LogonTime { get; set; }

        [Required]
        [MaxLength(40)]
        public string LogonIPAddress { get; set; }

        [Required]
        [MaxLength()]
        public string LogonUserAgent { get; set; }
    }    
}

それを DbContext に追加します。

namespace StartReg.Data {
    using System;
    using System.Collections.Generic;
    using System.Data.Entity;
    using System.Data.Entity.Infrastructure;
    using System.Linq;

    public partial class StartRegDb : DbContext {
        public StartRegDb()
            : base("DefaultConnection") {
        }

        public DbSet<Distance> Distances { get; set; }
    }
}

その後、パッケージ マネージャー コンソール (NuGet がインストールされていますか?) でコマンドEnable-MigrationsAdd-Miration Version1000実行すると、移行構成が表示されます。

namespace StartReg.Migrations {
    using System;
    using System.Data.Entity;
    using System.Data.Entity.Migrations;
    using System.Linq;
    using StartReg.Data;

    internal sealed class Configuration : DbMigrationsConfiguration<StartReg.Data.StartRegDb> {
        public Configuration() {
            AutomaticMigrationsEnabled = false;
        }

        protected override void Seed(StartReg.Data.StartRegDb context) {
            //  This method will be called after migrating to the latest version.
        }
    }
}

および Version1000 移行クラス:

名前空間 StartReg.Migrations { システムを使用。System.Data.Entity.Migrations の使用;

public partial class Initial : DbMigration {
    public override void Up() {

        CreateTable(
            "dbo.Distances",
            c => new {
                DistanceId = c.Guid(nullable: false),
                MeetingId = c.Int(nullable: false),
                Key = c.String(nullable: false, maxLength: 20),
                Name = c.String(nullable: false, maxLength: 100),
                Ordering = c.Short(nullable: false),
                AllowMale = c.Boolean(nullable: false),
                AllowFemale = c.Boolean(nullable: false),
            })
            .PrimaryKey(t => t.DistanceId)
            .ForeignKey("dbo.Meetings", t => t.MeetingId, cascadeDelete: true)
            .Index(t => t.MeetingId)
            .Index(t => new { MeetingId = t.MeetingId, Ordering = t.Ordering });
    }

    public override void Down() {
        DropTable("dbo.Distances");
    }
}

}

その後、データベースでの実際の作業の前にどこかに配置する必要があります(たとえば、Application_Start):

Database.SetInitializer(new MigrateDatabaseToLatestVersion<StartRegDb, StartReg.Migrations.Configuration>());

アプリを起動すると、テーブル Distances がデータベースに自動的に作成されます。

于 2013-03-17T17:00:49.740 に答える