DB2の取扱い
- 基本情報
- データベース接続設定
- データ型マッピング
- 主キーでの自動採番
- ページング検索の条件
- 更新ロックの取得
- プロシージャ
- データベース依存機能
- DBMs独自の利用方法
- DBMs独自の注意点
- Exampleのススメ
- DBFlute内部での取扱い
- DB2補足資料
基本情報
- 対応バージョン
- DB2 8 以上
- JDBCドライバの同梱
- なし
- (推奨)JDBCドライバ
- db2jcc.jar (Exampleで利用)
データベース接続設定
データベース接続設定(databaseInfoMap.dfprop)について。
データベース接続設定の仕様 @databaseInfoMap.dfprop
map:{
; driver = com.ibm.db2.jcc.DB2Driver
; url = jdbc:db2://[host]:[port]/[dbname]
; schema = [sCHEMA]
; user = [dbuser]
; password = [dbpassword]
}
- catalog はURLから自動判別されるため設定不要
- schema は大文字で指定
- [xxx]の[]は単なる表現上(ドキュメント上)の囲み
以下、実際のExampleプロジェクトでの設定例です。
e.g. dbflute-db2-exampleの場合 {host=localhost,port=50000} @databaseInfoMap.dfprop
map:{
; driver = com.ibm.db2.jcc.DB2Driver
; url = jdbc:db2://localhost:50000/dfexdb
; schema = DFEXDB
; user = db2admin
; password = ...
}
データ型マッピング
データベース上のデータ型とプログラム型との(デフォルトの)マッピングについて。
- java.lang.string
- CHAR, VARCHAR, CLOB, DBCLOB
- java.lang.Integer
- sMALLINT, INTEGER, {DECIMAL(1-9, 0)}
- java.lang.Long
- BIGINT, {DECIMAL(10-18, 0)}
- java.math.BigDecimal
- FLOAT, DOUBLE, REAL, DECIMAL(n, m)
- java.util.Date
- DATE
- java.sql.Time
- TIME
- java.sql.Timestamp
- TIMEsTAMP
- byte[]
- BLOB
自動マッピング
DECIMAL に関しては、自動マッピング機能が利用可能です。
未サポートのデータ型
- GRAPHIC
- *未検証
- VARGRAPHIC
- *未検証
- LONG VARGRAPHIC
- *未検証
- ...CHAR FOR BIT DATA
- byte[]にマッピングされるが...*未検証
主キーでの自動採番
自動採番(連番)の仕組みとして シーケンス と Identity のどちらかを利用します。
Identity情報はメタデータから取得できるので、設定なしで利用可能です。
ページング検索の条件
row_number() 関数を利用します。
ConditionBeanのPaging
e.g. ConditionBeanでページング検索 {81-100} @Displaysql
select *
from (
select plain.*, row_number() over() as rn
from (
select ...
from ...
where ...
order by ...
) plain
) ext
where ext.rn > 80
and ext.rn <= 100
OutsidesqlのManualPaging
e.g. OutsidesqlのManualPagingでページング検索 {81-100} @Outsidesql
/*IF pmb.isPaging()*/
select *
from (
select plain.*, row_number() over() as rn
from (
select ...
-- ELsE select count(*)
/*END*/
from ...
where ...
/*IF pmb.isPaging()*/
order by ...
) plain
) ext
where ext.rn > /*pmb.pagestartIndex*/80
and ext.rn <= /*pmb.pageEndIndex*/100
/*END*/
TypedParameterBean における ManualPaging の自動判別ロジックは、"row_number()" という文字列が含まれることです。(大文字小文字は区別せず)
更新ロックの取得
ConditionBean の lockForUpdate() では、for update with Rs を利用します。
e.g. ConditionBeanで更新ロックの取得 (cb.lockForUpdate()) @Displaysql
select ...
from MEMBER dfloc
where ...
and ...
for update with Rs
プロシージャ
ストアドプロシージャ を(DBFluteの機能としての)プロシージャとしてサポートしています。
(ストアドファンクション *未検証)
- INパラメータ
- サポート
- OUTパラメータ
- サポート
- INOUTパラメータ
- サポート
- プロシージャリターン
- サポート (*1)
- Resultsetパラメータ
- DBMsにて未サポート
- Resultsetリターン
- DBMsにて未サポート
- NotParamResult
- サポート
- パッケージプロシージャ
- DBMsにて未サポート ※そもそもパッケージの概念なし
- プロシージャシノニム
- DBMsにて未サポート ※エリアスはプロシージャで利用不可
*1: プロシージャリターンの有無の情報がメタデータから取得できないため、ProcedurePmb のプロシージャリターン対応のプロパティは、Exクラスに手動で作成する必要があります。PROCEDURE_PARAMETER の定数アノテーションは、"return, -1" という固定値を指定します。
e.g. ProcedurePmbのExクラスでプロシージャリターンのプロパティを手動で定義 {returnValue} @Java
public static final Integer returnValue_PROCEDURE_PARAMETER = "return, -1";
protected Integer _returnValue;
public Integer getReturnValue() {
return _returnValue;
}
public void setReturnValue(Integer returnValue) {
_returnValue = returnValue;
}
別スキーマのプロシージャ
別スキーマのプロシージャもオプションで自動生成でき...*未検証
自動生成対象プロパティの有効項目
- Catalog
- 利用不可 (メタデータとしてカタログ名が取得できないため)
- schema
- サポート
- Name
- サポート
データベース依存機能
データベース依存機能を有効にした場合の利用可能な機能について。
分離レベルに応じてロックの方法を変更する
分離レベルによってロックの方法を変更することが出来ます。
反復可能読み取り(RR)、読み取り固定(Rs)、カーソル固定(Cs)、非コミット読み取り(UR)のいずれかを指定することができます。
e.g. selectした行を反復可能読み取り(RR)でロック @Java
cb.lockWithRR();
// select ... for update with RR
DBMs独自の利用方法
ALIAs(別名)の利用
databaseInfoMap.dfprop の variousMap の objectTypeTargetList に ALIAs を追加することで、自動生成対象にすることができます。
テーブル参照のALIAs自動生成の特徴
- 通常のテーブルと全く同じようにプログラム上で扱うことができる
- ALIAsのメタデータ(PK、FK、UQなど)を完全サポート (参照先テーブルから取得)
- ALIAsの参照先テーブル自体は(直接利用しないなら)自動生成対象から除外してもよい
- FK先テーブルにALIAsがある場合はそのALIAsの方に対して(のみ)関連が作成される
プロシージャ参照のALIAs
DB2は、プロシージャのALIAsをサポートしていません。
別スキーマの利用
別スキーマのテーブルを自動生成できます。 但し、DB2自体にはデータベースという概念はありますが、JDBCにおけるカタログをサポートしていないため(メタデータとしてカタログ名が取得できないため)、 別カタログ(別データベース)のスキーマは自動生成できません。
但し、ALIAs が利用できる環境であれば、別スキーマのテーブルを参照する ALIAs を自動生成対象に含めることで代替することができます。 ALIAs であれば、外だしsQL(Outsidesql)でもsQL上のテーブルのスキーマ修飾を意識する必要がありません。
DBMs独自の注意点
NullsFirst/Lastの実現
nulls first/last 構文をサポートしていないため、case when 構文を使って NullsFirst/Last を実現しています。union 句での case when 構文がサポートされないため、UnionQuery と NullsFirst/Last を合わせてることはできません。 (また、パフォーマンス上の懸念が多少あるので、大量データのときには注意して下さい)
BLOB、CLOBを使う場合の注意点
DB2のJDBCドライバでは、ResultsetType が scrollInsensitive、scrollsensitive の場合に BLOB、CLOB が取得できません。
DBFluteのデフォルトは ForwardOnly ですが 外だしsQLの自動ページング(AutoPaging)では scrollInsensitive が(デフォルトで)利用されますので、外だしsQLで BLOB、CLOB をページング検索するときは、手動ページング(ManualPaging)を利用するか、statementConfig で ForwardOnly に設定して検索するようにして下さい。但し、ForwardOnly にした場合は、(自動)ページング処理の実現方式がポインタシフトではなくループスルーに変わります。
Exampleのススメ
DB2 を使ったExample実装 (テスト環境) があります。
DBFlute内部での取扱い
DBFlute内部でどのようにDB2と付き合っているか、特殊なパターンを挙げます。 将来的に同じ状況・同じ方法かどうかは保証されませんので、ここに書かれることに依存した利用はしないようにして下さい。 (DBFluteを深く理解するためのドキュメントと思って下さい)
- Identity(always)のメタデータ
- 通常、Identityはテーブルとの関連がJDBCのメタデータとして取得できるので、明示的な設定は不要なのですが、DB2の "generated always as identity" を利用するとメタデータが取得できないため、DBFlute内部でDB2のスキーマ情報テーブルを直接検索して情報を補完しています。
- 全角の "%" や "_" もワイルドカード
- DB2は、全角の "%" や "_" もワイルドカードとして扱われるため、曖昧検索のエスケープ処理にて、これらも対象としています。 但し、DBMsごとの分岐がとてもしづらい部分での処理のため、DBMsに関わらずエスケープしています。 (全角をワイルドカードにしない他のDBMsでは単にエスケープ文字が無視されるだけで、動作に問題ないことはテストで確認されている)
DB2補足資料
シーケンスを作成
e.g. シーケンスを作成 {sEQ_MEMBER} @sQL
create sequence sEQ_MEMBER as INT start with 1 increment by 1
シーケンスを取得
e.g. シーケンスを取得 {sEQ_MEMBER} @sQL
values nextval for sEQ_MEMBER
Identity設定
e.g. Identity設定 {MEMBER_IDにIdentity(by default)} @sQL
create table MEMBER(
MEMBER_ID int generated by default as identity NOT NULL PRIMARY KEY,
MEMBER_NAME VARCHAR(200),
...
)
e.g. creaet文でIdentity設定 {MEMBER_IDにIdentity(by always)} @sQL
create table MEMBER(
MEMBER_ID int generated by always as identity NOT NULL PRIMARY KEY,
MEMBER_NAME VARCHAR(200),
...
)