Entity Framework Core でエンティティクラスを別のプロジェクトに分ける方法

運濃すぎる。分けたらマイグレーションできなくなった。一週間前これで退社できず昼夜逆転しまだ直りません。

Targeting class library projects is not supported

ここで書かれてるようなイケてるエラーは出なかったけどな。早く fix して。対処方法しか見つからなかったのですが、マイグレーションできないそのプロジェクトを実行可能にしろってことみたいです。

エンティティクラスをまとめた (あと DB コンテキスト) プロジェクトの project.json は以下のようになりました。ASP.NET Core Identity 使ってるので関係無いものも含まれてます。

{
    "dependencies": {
        "Microsoft.AspNetCore.Identity.EntityFrameworkCore": "1.1.0-preview1-final",
        "Microsoft.EntityFrameworkCore.SqlServer": "1.1.0-preview1-final",
        "Microsoft.EntityFrameworkCore.SqlServer.Design": {
            "version": "1.1.0-preview1-final",
            "type": "build"
        },
        "Microsoft.EntityFrameworkCore.Design": {
            "version": "1.0.0-preview2-final",
            "type": "build"
        },
        "Microsoft.EntityFrameworkCore.Tools": {
            "version": "1.0.0-preview3-final",
            "type": "build"
        }
    },
    "tools": {
        "Microsoft.EntityFrameworkCore.Tools": "1.0.0-preview3-final"
    },
    "frameworks": {
        "net462": {}
    },
    "buildOptions": {
        "emitEntryPoint": true
    }
}

"emitEntryPoint": true が味噌らしいです。あとはパッケージ周りのエラーを見ながら必要なパッケージを追加します。で、エントリポイント発行のため空のエントリポイントを追加します。

public static class Program
{
    public static void Main (string[] args)
    {
        // 実行しないので書く必要が無い
    }
}

最後に IDbContextFactory{TDbContext} を実装したクラスをどこかに置いておきます。IdentityDbContext{TUser} を継承しているのでこのように対処しました。

public sealed class DbContextFactory : IDbContextFactory<DbContext>
{
    public DbContext Create (DbContextFactoryOptions options)
    {
        var builder = new DbContextOptionsBuilder<DbContext> ();

        //
        // ...
        //
        // DB コンテキストを初期化します。
        // builder は DbContext{T}.OnConfiguring の引数と同じ。
        //

        return new DbContext (builder.Options);
    }
}

Add-Migration で素っ気ないエラーが出る場合 (一行だけの Built error. みたいな奴だったと思うけど忘れた)、僕の場合はコードにバグがあるかパッケージ不足が原因でした。コードとパッケージが問題なく、リレーションなどの不具合が原因ならマイグレーション追加時にちゃんと報告してくれます。