次のようなことをすることは有効ですか?
CREATE SYNONYM [dbo].[MyTable] FOR [AnotherDatabase].dbo.[MyTable]
次に、Entity Frameworkのedmxファイルを変更して、他のテーブルと同じようにこのオブジェクトを読み取りますか?
簡単なサンプルテストを行ったところ、選択と更新には問題なく機能しているようですが、これを行うべきではない理由があるかどうかを知りたいと思いました。
2番目のデータベースを指すedmxファイルを作成し、そこにエンティティを構築してから、定義をコピーして1番目のデータベースのedmxファイルに貼り付けることで、テーブル定義を取得しています。
[〜#〜]更新[〜#〜]
誰かが興味を持っているなら、私はedmxファイルを複数のデータベースにまたがらせるために私がしたことを書きました ここ 。同義語を生成し、edmxファイルをマージするためのスクリプトが含まれています。
あなたがテストをしてそれがうまくいったなら、あなたはおそらく他の誰も知らない何かを示したでしょう。これまで、私は常にこのタイプの質問に答えていました。2つのデータベースで単一のモデルを使用することはできません(2番目のデータベースからテーブルを隠すビューに基づくいくつかのより醜い回避策があります)。今、私は2つの回避策を知っています。
このアプローチの唯一の欠点は、データベースからモデルを更新を実行すると、EDMXのSSDL部分に手動で加えられたすべての変更が常に失われることです。これは、EDMXを手動で開発するか(非常に大変な作業です)、データベースから更新するたびに変更を追加するツール/スクリプトを使用することを意味します。
ビュー(および他のデータベースが別のサーバー上にある場合はリンクサーバー)を使用してこれを行うこともできます。これにより、2つの別々のedmxファイルを管理/マージする必要がなくなります。リンクサーバーでこれを使用して、別のサーバー上の2番目のデータベースからデータを読み取りましたが、いくつかの簡単なテストを実行して、更新/挿入/削除が可能かどうかを確認しました。
私は分散トランザクションの経験がないので、分散トランザクションに関連する情報は良い、悪い、または両方の少しかもしれません。2つのデータベースが同じサーバー上にある場合I [〜#〜]仮定[〜#〜]分散トランザクションは適用されなくなります。
リンクサーバーを使用する際に留意すべき点がいくつかあります。
SaveChanges
を呼び出すと、分散トランザクションが開始されます。そのため、誰かがそれを停止する方法を知らない限り、2つのサーバーが次のように設定されていることを確認する必要があります。分散トランザクションを処理します。 (これは同義語を使用しても当てはまると思います)。SCOPE_IDENTITY()
を使用して新しいIDを取得しようとし、それがnullであるため、例外をスローします。これを回避する方法があるかどうかはわかりません。 ID列を持つリンクサーバー上のエンティティの更新または削除に問題はありませんでした。SQL Server Aの場合
[ServerA].[MyDB]
のテーブルごとに[ServerB].[AnotherDB]
にビューを作成しますEDMXの場合
更新/挿入/削除の場合
StorageModel
-> Schema
-> EntityContainer
に移動しますDefiningQuery
要素を削除しますstore:Schema
属性を見つけ、store:
を削除してSchema
になるようにします。その値はそのままにしておきます。リンクサーバーを使用すると分散トランザクションが作成されるため、ObjectContext
が成功する前に、SaveChanges
でいくつかのことを行う必要がありました。
ctx.Connection.Open();
ctx.ExecuteStoreCommand("set xact_abort on");
ctx.SaveChanges();
ctx.Connection.Close();
おそらく、カスタムObjectContext
を作成し、SaveChanges
をオーバーライドしてこのようなものを追加することができます。
同義語を使用したこのトリックは、edmxファイルを操作しなくても、「コードファースト」アプローチで完全に機能することがわかりました。
あなたがしなければならない唯一のことは、DataContextのOnModelCreatingメソッドでクラスを適切なシノニムに「バインド」することです。
たとえば、テーブルPersonnel別のDB(およびクラス名もPersonnel)で、シノニムの名前が "myschema.MySynonym"の場合、OnModelCreatingメソッドは次のようになります。
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.HasDefaultSchema("myschema");
modelBuilder.Entity<Personnel>()
.ToTable("MySynonym");
Database.SetInitializer<TestSynonymContext>(null);
base.OnModelCreating(modelBuilder);
}