データベースアクセスがある場合は、DBUnit を使うのがベストなんでしょうが、ひとまず、初期データの投入だけできればいいや、って気持ちで作ったのがこれです。
public class DBTest { public static void DataSetup( IDataTable tbl, SqlConnection cn ) { Type RowType = tbl.GetRowType(); string TableName = tbl.GetTableName(); PropertyInfo[] pis = typeof(XProductRow).GetProperties(); string sql_columns = "("; string sql_values = "("; foreach (PropertyInfo pi in pis) { sql_columns += pi.Name + ","; sql_values += "@" + pi.Name + ","; } // 最後のカンマを削除 sql_columns = sql_columns.Substring(0, sql_columns.Length - 1); sql_values = sql_values.Substring(0, sql_values.Length - 1); string sql = "insert into " + TableName+ " " + sql_columns + ") values " + sql_values + ")"; SqlCommand cmd = new SqlCommand(sql, cn); foreach (PropertyInfo pi in pis) { SqlParameter param = new SqlParameter(); param.ParameterName = pi.Name; cmd.Parameters.Add(param); } cmd.Connection.Open(); foreach ( object item in tbl.GetList()) { foreach( PropertyInfo pi in pis ) { cmd.Parameters[pi.Name].Value = pi.GetValue(item,null); } cmd.ExecuteNonQuery(); } cmd.Connection.Close(); } }
例のごとく、リフレクションを使ってプロパティ名=テーブルのカラム名と想定して、INSERT 文を作成します。Visual Studio で作成される型付 DataSet を使っても良いのですが、データ投入をするたびに、別の DataAdapter を呼び出さないといけないし、なんかいまいちなので、ってのと、テストデータの投入なので INSERT 文と、テーブルの中身を DELETE する部分だけが欲しい訳で、型付 DataSet だと冗長なんですよね。
/// <summary> /// リフレクションが簡単になるためのインターフェース /// </summary> public interface IDataTable { string GetTableName(); Type GetRowType(); System.Collections.IList GetList(); } /// <summary> /// 商品クラス(カラム) /// </summary> public class XProductRow { public string id { get; set; } public string name { get; set; } public int price { get; set; } public int cateid { get; set; } } /// <summary> /// 商品クラス(テーブル) /// </summary> public class XProduct : IDataTable { public XProduct() { Rows = new List<XProductRow>(); } public List<XProductRow> Rows { get; set; } public Type GetRowType() { return typeof(XProductRow); } public System.Collections.IList GetList() { return this.Rows; } public string GetTableName() { return "XProduct"; } public XProductRow NewRow() { return new XProductRow(); } }
ざっくりと、POJO タイプの DataRow と、単なるコレクションを集めただけの DataTable を作っておきます。
そうして、データ投入をする場合は、
private void button1_Click(object sender, EventArgs e) { // 自動でinsert文を作る SqlConnection cn = new SqlConnection(@"Data Source=.\sqlexpress;Initial Catalog=mvcdb;Integrated Security=True;MultipleActiveResultSets=True"); XProduct table = new XProduct(); XProductRow it = table.NewRow(); it.id = "A8000"; it.name = "新商品XXX"; it.price = 2000; it.cateid = 2; table.Rows.Add(it); it = table.NewRow(); it.id = "A8001"; it.name = "新商品YYY"; it.price = 2000; it.cateid = 2; table.Rows.Add(it); DBTest.DataSetup(table, cn); }
こんな風に、DataRow/DataTable にデータを詰めておいて、一気にセットアップできます。
C# v3.0 の場合は、こんな風に初期化しながらということもできます。
table.Rows.Add( new XProductRow { id = "A8002", name = "新商品ZZZ", price = 20000, cateid = 1 });
まあ、これで良いかなぁと。