Location via proxy:   [ UP ]  
[Report a bug]   [Manage cookies]                
ラベル db の投稿を表示しています。 すべての投稿を表示
ラベル db の投稿を表示しています。 すべての投稿を表示

2011年7月31日日曜日

(小ネタ)システムコントロールテーブルは必ず用意しましょう

システムを構築すると、必ず「設定値」が必要になります。

・1ページの表示行数
・XXした際の遷移先URL
・YY通信のタイムアウト時間
...etc

上記設定をどこに置くかは結構大きな問題です。

(例)
①propertiesファイル (javaの場合)
②xxx.rbファイル (rubyの場合)
③データベース
...

上記①や②は最速ですが、設定値の反映には「アプリケーションの再デプロイ or 再起動」が必要になります。よって気軽に変更値の変更という訳にはいきません。

③はデータベースへの問い合わせが必要ですが、アプリケーション実行時に設定値を切り替えられるという利点があります。この手の設定値テーブルを用意しておくと顧客との打合せ時に、無駄な値決めに時間を浪費する事を回避できるというメリットもあります(顧客は情報がそろってから意思決定できるようになるので)。

よって、システムを開発してusersテーブルを作成した次には(?)、上記テーブルを作成しましょう。(心の)師匠、渡辺幸三さんに敬意を評し、「システムコントロール」テーブルと名づけましょう。

system_controls
----
code (PK or UK)
value (設定値)
editable (ユーザが画面上より編集可能か?)
description (編集画面での説明文章)
type (文字列、数字、boolean等入力タイプの区分値。多くなるならドメインテーブル作成。入力チェックと絡めるのも良いかもですね)
updater_id (最終更新者)
updated_at (最終更新日時)

こんな感じかな?

スピードが気になる人は、上記のcode値を利用して、KVSとかキャッシュサーバに突っ込めば良いでしょう。
# 変更、破棄タイミングに気をつけて下さい

ちなみに上記目的のテーブルを横持ち(カラム)で持ちたがる人がいますが、全力で阻止しましょう。柔軟にcodeを追加出来るのがミソなので!!

後DB障害発生時に問い合わせられない事も意識する必要があります(例 例外メール送信先)ので注意が必要です。

2011年5月21日土曜日

論理データベース設計(ER図)のチェックリスト

■概要

職業がら、顧客と会話しデータベースの論理設計をする事が良くあります。
自分で設計する分には良いんですが、他人が設計した物を効率的にチェックする為に備忘録がてら記載しておきます。

ちなみに当方は「渡辺幸三さんの著作」と「アナリシスパターン」の影響を一番受けています。

■チェック項目
○キーについて
・データの一意性が、利用者(顧客)と意識があっているか
・PKの無いテーブルはないか
・UKが明示されているか
・多すぎる複合キーはないか
・自然キーとサロゲートキーを意識できているか
・ID / コード・番号を使い分けているか
・FKを意識できているか
・FK/区分との使い分けは考えられているか
・属性項目のドメインを規定する物なので使い分けの基準が重要

○属性について
・ドメイン管理を意識して属性名を付けているか
・継承項目、導出項目が明示されているか
・継承・導出ルールが明示・意識されているか
・時点記録を意識して導出項目を設計しているか?

○多重度・関係について
・多重度が間違っていないか
・1-1関連が存在しないか
・"0以上"なのか"1以上"なのか考察できているか
・親子と参照を意識して使っているか
・派生関係を意識できているか

○正規化について
・繰り返し項目が除去できているか(もしくは意識できているか?)
・PKからの関数従属性のみになっているか
・キー組み合わせについてデータが表現出来ているか

○その他について
・インスタンスレベルでイメージできているか
・インスタンスにするべき概念がテーブルになってないか
・パラレルに重複した構造・関係はないか
・プログラムとの連携を意識できているか
・知識・操作レベルを意識できているか
・データのライフサイクルを意識できているか
・区分が設計されているか
・状態の管理が意識できているか
・人間はミスをするという事を意識できているか
・業務にキャンセルがありえる事を意識できているか

■雑感

思いつくまま記載しても結構あるな。思い出したら追加していこう。。

2011年4月6日水曜日

indexを作成すると本当に更新性能は下がるのか?

■概要
RDBMSの参照性能を向上させる為に、indexを作成する事は常識だと思います。
ところが「indexを張りすぎると更新性能が悪くなる」と言われており、理屈的にも理解できます(データおよびindexを更新する必要があるから)。
しかし実際どの程度劣化するのか知りたいので、実験してみたいと思います。

■前提
・さくらVPS 512Mコース
・CentOS 5.x
・mysql 5.0.77
・利用テーブル(下記の様なテーブルで順次indexを作成しなおしテストした)
drop table test_table;
create table test_table (
  id integer auto_increment not null
, v1 varchar(30) not null
, v2 varchar(30) not null
, v3 varchar(30) not null
, v4 varchar(30) not null
, v5 varchar(30) not null
, primary key(id)
);
--create index v1_index on test_table(v1);
--create index v2_index on test_table(v2);
--create index v3_index on test_table(v3);
--create index v4_index on test_table(v4);
--create index v5_index on test_table(v5);
・テストデータ 10万件insert (下記の様なrubyスクリプトを作成し出来上がったinsert.sql文ファイルを実行した)
def random_string(len)
  (0...len).map{ ('a'..'z').to_a[rand(26)] }.join
end

open("insert.sql", "wb") do |f|
  f.write("truncate table test_table;\r\n")
  f.write("set @time:=now();\r\n")
  (0...100000).each do |i|
    v1 = random_string(30)
    v2 = random_string(30)
    v3 = random_string(30)
    v4 = random_string(30)
    v5 = random_string(30)
    vals = "'" << [v1, v2, v3, v4, v5].join("','") << "'"
    f.write("insert into test_table (v1, v2, v3, v4, v5) values (#{vals});\r\n")
    puts i
  end
  f.write("commit;\r\n")
  f.write("select timediff(now(), @time);\r\n")
end

$ mysql -u xxx < insert.sql

■結果

index数 1回目 2回目 3回目 4回目 5回目 平均処理時間(秒)
0
15
20
14
10
14
12.6
1
19
18
16
15
14
16.4
2
15
14
18
18
15
16.0
3
18
14
17
20
21
18.0
4
23
18
18
19
18
19.2
5
19
22
19
24
20
20.8



■結論

確かに下がるには、下がるようだ。。という訳でセオリー通りindexの張りすぎには注意が必要のようです。

ただ全体的にy = ax + bの一次関数likeな上昇なので、"+b"がどこに消費されるのかが気になるところです(sql文のparse?)