web-dev-qa-db-ja.com

複数のDBスキーマでEntity Framework 6を​​使用するが、1つのDBContextを使用する

EFをORMとして使用するアプリケーションがあります。以前はデータベースに1つのスキーマdboがあり、すべて正常に機能していました。最近、テーブルを4つの異なるスキーマに編成しました。 1つのスキーマの一部のテーブルは、異なるスキーマにあるテーブルに依存しています。すべてはSQL側で有効なようです。

アプリ側では、EFを介したすべてのdbインタラクションが機能しなくなりました。コードがコンパイルされ、スキーマがソリューションに表示され、モデルマッピングが適切なスキーマを指しますが、テーブルに行を挿入しようとすると機能しません。

複数のスキーマを使用することに関する複数の投稿を見てきましたが、複数のDBContextを使用する必要がありますが、1つのDBContextを使用します。すべてのスキーマの所有者dboが同じであり、複数のDBContextを使用する理由がわかりません。

これを達成する方法があるかどうか誰もが知っていますか?

29
Apollonas

Fluentマッピングのみで、各テーブルを独自のスキーマにマッピングできます。 DbContextサブタイプでは、OnModelCreatingをオーバーライドして(まだ行っていない場合)、次のようなステートメントを追加する必要があります。

modelBuilder.Entity<Department>()  
    .ToTable("t_Department", "school");

このように明示的にマッピングしないエ​​ンティティは、デフォルトのdboスキーマに配置されます。または、独自のデフォルトを提供できます

modelBuilder.HasDefaultSchema("sales");

here から要約)

30
Gert Arnold

Gert Arnoldの応答に加えて、エンティティでTable属性を使用することもできます。

using System.ComponentModel.DataAnnotations.Schema;

[Table("t_Department", Schema = "school")]
public class Department
{
    public int Id { get; set; }

    public string Name { get; set; }
}
20
Stas Boyarincev

@GertArnoldは、彼の答えにスポットを当てています。ただし、純粋な構文キャンディーの場合は、モデルの名前空間からスキーマをプルする規則を介してこれを行うこともできます。これは複数のスキーマを扱うのに便利だとわかりました

modelBuilder.Types().Configure(e => {
        var schema = e.ClrType.Namespace.Split('.').Last().ToLower();
        var name = entity.ClrType.Name;
        return entity.ToTable(name, schema);
});

上記は、名前空間の最終コンポーネントを取得し、それをスキーマ名として使用します。これにより、すべてのエンティティのテーブルバインディングをカスタマイズする必要がなくなります。

8
Luke McGregor

クラスヘッダーなどのスキーマを配置しますが、そのスキーマをどこに定義しますか?例えば:

[Table("Test", Schema = "test1")]
public class Test
{
    public int Id { get; set; }
}

[Table("Test2", Schema = "test2")]
public class Test2
{
    public int Id { get; set; }
}

しかし、どこにtest1とtest2を配置しますか?異なるDbContextまたはどこですか?

0
Alex