VS2005環境でのNAgile - テーブル間のリレーションシップのテスト
今日はデータ テーブル間のリレーションシップのテストを行った。
まずこのテストを行う前の状況を説明しておく。
SQL Server 2005の全てのリレーションシップのINSERTおよびUPDATEの指定は、次のようなデフォルト指定になっている。
- DeleteRuleの指定・・・動作なし
- UpdateRuleの指定・・・動作なし
よって自動生成された型付DataSetのDataRelationも次のようなデフォルトのままだ。
- 作成する制約の選択・・・リレーションシップのみ
次に現状のリレーションシップを以下のように変更していくことにする。
- 外部キーの制約として親レコードが削除されたときは子レコードの外部キーをNULLにする。
- 外部キーの制約として親レコードが更新されたときは子レコードの内容も更新させる。
このテストは次のような手順で行った。
最初のタスク:外部キーの制約として親レコードが削除されたときは子レコードの外部キーをNULLにする。
- テストメソッドを記述してテストが失敗することを確認する。
- データベースダイアグラムで対象のリレーションシップを選択してプロパティを開く。
- INSERTおよびUPDATEの指定のDeleteRuleの設定で「Nullに設定」を選択する。
- 子テーブルの外部キーのNullを許容を「はい」に設定する。
- データベースに変更を反映させる。
- データセットデザイナで対象のリレーションシップを選択し、リレーションの編集メニューからリレーションシップダイアログを開く。
- 作成する制約の選択で「リレーションシップと外部キー制約の両方」を選択する。
- ルールの削除で「SetNull」を選択する。
- 子DataTableの外部キーフィールドのAllowDBNullをTrueに設定する。
- テストを走らせて成功することを確認する。
次のタスク:外部キーの制約として親レコードが更新されたときは子レコードの内容も更新させる。
- テストメソッドを記述してテストが失敗することを確認する。
- データベースダイアグラムで対象のリレーションシップを選択してプロパティを開く。
- INSERTおよびUPDATEの指定のUpdateRuleの設定で「重ねて表示」を選択する。
- データベースに変更を反映させる。
- データセットデザイナで対象のリレーションシップを選択し、リレーションの編集メニューからリレーションシップダイアログを開く。
- UpdateRuleの設定で「Cascade」を選択する。
- テストを走らせて成功することを確認する。
以下は作成されたテスト
using System; using System.Text; using System.Collections.Generic; using Microsoft.VisualStudio.TestTools.UnitTesting; using System.Data; using Library.DataAccessLayer; using Library.DataAccessLayer.LibraryDataSetTableAdapters; using System.Transactions; namespace Library.Tests.DataAccessLayer.Relations { [TestClass] public class BooksCategoriesRelationTest { private LibraryDataSet ds_; private TransactionScope ts_; private CategoriesTableAdapter cta_; private BooksTableAdapter bta_; [TestInitialize] public void CreateTransactionScope() { ts_ = new TransactionScope(); ds_ = new LibraryDataSet(); cta_ = new CategoriesTableAdapter(); cta_.Fill(ds_.Categories); LibraryDataSet.CategoriesRow category = ds_.Categories.AddCategoriesRow(1, "オブジェクト指向型開発"); cta_.Update(category); bta_ = new BooksTableAdapter(); bta_.Fill(ds_.Books); LibraryDataSet.BooksRow book = ds_.Books.AddBooksRow("4-7741-2728-0", "LifeHacks PRESS", "百式の中の人ほか", "なし", category); bta_.Update(book); } [TestCleanup] public void DisposeTransactionScope() { ts_.Dispose(); } [TestMethod] public void カテゴリーテーブルのレコードが削除された場合は書籍テーブルのカテゴリーIDはDBNullになるべき() { LibraryDataSet.CategoriesDataTable existCategoies = cta_.GetDataByCategoryId(1); existCategoies[0].Delete(); cta_.Update(existCategoies[0]); LibraryDataSet.BooksDataTable existBooks = bta_.GetDataByIsbn("4-7741-2728-0"); Assert.IsTrue(existBooks[0].IsCategoryIdNull()); } [TestMethod] public void インメモリでカテゴリーテーブルのレコードが削除された場合でも書籍テーブルのカテゴリーIDはDBNullになるべき() { LibraryDataSet.CategoriesRow existCategory = ds_.Categories.FindByCategoryId(1); existCategory.Delete(); LibraryDataSet.BooksRow existBook = ds_.Books.FindByIsbn("4-7741-2728-0"); Assert.IsTrue(existBook.IsCategoryIdNull()); } [TestMethod] public void カテゴリーテーブルのカテゴリーIDが更新された場合は書籍テーブルのカテゴリーIDも更新されるべき() { LibraryDataSet.CategoriesDataTable existCategoies = cta_.GetDataByCategoryId(1); existCategoies[0].CategoryId = 2; cta_.Update(existCategoies[0]); LibraryDataSet.BooksDataTable existBooks = bta_.GetDataByIsbn("4-7741-2728-0"); Assert.AreEqual<int>(2, existBooks[0].CategoryId); } [TestMethod] public void インメモリでカテゴリーテーブルのカテゴリーIDが更新された場合でも書籍テーブルのカテゴリーIDも更新されるべき() { LibraryDataSet.CategoriesRow existCategory = ds_.Categories.FindByCategoryId(1); existCategory.CategoryId = 2; LibraryDataSet.BooksRow existBook = ds_.Books.FindByIsbn("4-7741-2728-0"); Assert.AreEqual<int>(2, existBook.CategoryId); } } }
#リレーションシップ毎にこのようなテストクラスを作成した。