10個以上のテーブルをアクセスするアプリで、テーブルの管理を楽にしたいと思っていろいろ試したことを記録する。
現状
整理する前の状況は以下のような感じ。
- C#のソースファイルの中に、SQLの「Create Table」文の文字列がずらずらと書いてある。
- SQLServer Management Studio(SSMS)が、テーブルから作ってくれるCreate Table文をそのまま貼ってある(らしい)。
- 初期値が必要なテーブルは、それに続いて、insert文も書いてある。
- アプリが動くときに、これらのSQLを実行する
- 何度も実行するとエラーになるので、テーブルの有無を調べて、無ければSQLを実行している
問題と思うことは、下記の通り。
- SQL文がずらずらと書いてあって読みにくい。
- どこで何のテーブルを作っているのか、わかりにくい。
- SSMSが自動生成したSQLに知らないキーワードがずらずらと書いてあるのが気になる。間違いではないのだろうけどなにが書いてあるのかわからない。インデックスや外部参照にいちいち名前を付けて作っているし。
- とにかくメンテがやりにくい
具体例で示すと、テーブルを作っているC#のソースファイルの全体像が下図。(VisualStudioはソースの全体像を表示できるのだ)。このファイルは2700行もあって、茶色はSQLが書かれた文字列で、ほとんどがSQLとわかる。
これだけSQLだと、外部のテキストファイルにSQLをまとめて、それを実行するようにした方がよさそうな気もする。
ただ、このアプリの制約として、テーブルは同じものを別の名前でたくさん作る必要がある。たとえば、年度ごとにテーブルAをいくつも作る感じ(TableA_2018、TableA_2019のような)。
つまり、SQLは一度動かせば完了ではなくて、年度をパラメータとして、何度も動かす必要があって、外部のSQLファイルにしするのは難しいように思える。(まあ、実行するときにパラメータを渡すようにすればよさそうだけど。)
テーブルごとにクラスを作ってみた
改善の一歩として、テーブルごとにクラスを作ってみた。クラスはテーブル名とテーブルを作るSQLをプロパティとして持つ。アプリの都合によりテーブル名は番号付きの接頭辞が付くという形式。(例)mm001_XXXinternal class mmTable_A : mmTable
{
internal mmTable_A(int yy)
{
this.yy = yy;
this.tableName = string.Format("mm_A_{0:000}", yy);
this.sqlCreate = @"
create table [{table_name}]
(
[A_id] [int] NOT NULL primary key,
[A_実施日] [datetime] NULL,
(中略)
); ";
}
}
これで、テーブルに関することはクラスで管理できる。基底クラスに、テーブルを作るメソッドや、削除するメソッドがあって、以下のように使う。
List<mmTable> lst = new List<mmTable>()
{
new mmTable_A(2018),
new mmTable_B(2018),
new mmTable_C(2018),
(中略)
};
foreach (mmTable tbl in lst)
{
tbl.doCreate();
}
SQL文の文字列がずらずらと書いてある状態よりは、ましになった。
(続く)
(続く)
コメント
コメントを投稿