2011-03-15 12 views
5

最新のEFコード最初のNuGetパッケージにはDontDropDbJustCreateTablesIfModelChangedと呼ばれるIDatabaseInitializerのカスタム実装が付属しています。この名前が示すように、モデルの変更が検出されると、データベース全体を削除して再作成せず、テーブルを削除して再作成します。EFコードのカスタム初期化戦略最初に列を追加するテーブルを削除しない

は、私は、このモデルクラスを持っていると言う:

public class User 
{ 
    public string Username { get; set; } 

    // This property is new; the model has changed! 
    public string OpenID { get; set; } 
} 

どのように1はIDatabaseInitializerそのは、任意のテーブルを削除いずれかしない実装に行きますか。この場合、OpenID列をUserテーブルに追加するだけですか?

答えて

5

私はそれがSQLの問題だと思います。だから、SQL Serverの次のような何か書くことができます。

public class MyInitializer : IDatabaseInitializer<MyContext> 
{ 
    public void InitializeDatabase(MyContext context) 
    { 
     context.Database.SqlCommand(
      @" 
      IF NOT EXISTS (SELECT 1 FROM sys.columns AS col 
          INNER JOIN sys.tables AS tab ON tab.object_Id = col.object_Id 
          WHERE tab.Name = 'User' AND col.Name = 'OpenId') 
      BEGIN 
       ALTER TABLE dbo.User ADD OpenId INT; 
      END"); 
    } 
} 

をしかし、同じようにあなたは私がより良いアプローチだと思う、あなたのアプリケーションに追加することなく、そのようなスクリプトを実行することができます。

+0

はい、利用可能なすべてのIDatabaseInitializer実装がより「破壊的な」アプローチを選択した方法を見ています。ありがとう –

+0

@Sergi Papaseit:これは非常に興味深いものです。あなたはそれ以上それを取った? EF 4.1のコードに最初に実装されたことの1つは、データベースの移行です。私は上のLadislavによって提示されたものが、それが何かに自動化されて何らかの形で自動化されるならば、実際に働くことができると信じています。だから、これ以上進んでいないなら、私たちと共有してください:) – Kassem

+0

@カッセム - 私は実際にはありません。誰かがここで私に非常に良い点を作っています。これはもちろん開発環境向けのものだから、毎回dbを落とすのは面倒ではありません。 ;) –

2

現在のバージョンのコードファーストでは、スキーマを修正して、テーブルにある可能性のあるデータを保持するだけではいけません。このような参照データ/ルックアップテーブルなどのデータを、維持することは、このリリースで重要である場合は、独自の初期化子を作成し、

public class MyDbInitializer : DropCreateDatabaseIfModelChanges<MyContext> 
{ 
    protected override void Seed(MyContext context) 
    { 
     var countries = new List<Country> 
     { 
      new Country {Id=1, Name="United Kingdom"}, 
      new Country{Id=2, Name="Ireland"} 
     }; 

     countries.ForEach(c => context.Countries.Add(c)); 
    } 
} 

をあなたのテーブルを移入してからのApplication_Startでこれを使用するために種子メソッドをオーバーライドすることができます

Database.SetInitializer<MyContext>(new MyDbInitializer()); 

私はこれが現在EFチームによって対処されていると思いますが、コードファーストドロップがリリースされた時点ではリリース準備ができていませんでした。ここでプレビューを見ることができます:Code First Migrations

関連する問題