H2databaseでORACLE関数をシミュレートする

ボクが仕事で絡むシステムでは、ORACLEをデータベースとして使用するものが多い。
そんなシステムでも、単体テストの段階では、スタンドアローンのデータベースを使用したい。エキセントリックなコードで謎データを作り上げてしまうことも多々あるし、手でデータをぶっ込みまくったりもしたいからだ。
でも、スタンドアローン版のORACLEは高い。しかたなく、フリーのデータベースであるH2databaseを使うことになる。

ただ、H2databaseには、TO_DATE等、ORACLEでSQLを書く時に頻繁に使用する関数すら無いため、実行できないSQLが出てくる。

色々試行錯誤した結果、H2databaseにあるaliasという機能を使って、関数をシミュレートすることで、ある程度は何とか出来るようになった。
ボクは、頻繁に使用する関数のTO_DATE、TO_CHAR、TO_NUMBERのエイリアスを常に入れておくようにしている。

以下のコードだ。
これだけでは心細いが、だいぶ適用できる幅が広がる。

  • TO_DATE
drop alias if exists TO_DATE;
create alias TO_DATE as $$
import java.text.*;
@CODE
java.util.Date toDate(String s, String dateFormat) throws Exception {
  if ( dateFormat.contains("MON")) {
    dateFormat = dateFormat.replace("MON", "MMM");
  }
  if ( dateFormat.contains("Y")) {
    dateFormat = dateFormat.replace(Y", "y");
  }
  if ( dateFormat.contains("D")) {
    dateFormat = dateFormat.replace("D", "d");
  }
  return new SimpleDateFormat(dateFormat).parse(s);
$$
  • TO_CHAR
drop alias if exists TO_CHAR;
create alias TO_CHAR as $$
import java.text.*;
Import java.util.Date;
@CODE

String toChar(String date, String pattern) throws Exception {
  pattern = pattern.replaceAll("YY", "yy");
  pattern = pattern.replaceAll("DD", "dd");
  pattern = pattern.replaceAll("HH24|hh24", "HH");
  pattern = pattern.replaceAll("HH?!24|hh?!24", "KK");
  pattern = pattern.replaceAll("MON|mon", "MMM");
  pattern = pattern.replaceAll("MI|mi", "mm");
  pattern = pattern.replaceAll("SS", "ss");
  pattern = pattern.replaceAll("AM|PM", "aa");

SimpleDateFormat sm = new SimpleDateFormat(pattern);
java.util.Date dt;
if (date.length() >10) 
  dt = java.sql.Timestamp.valueOf(date);
else 
  dt = java.sql.Date.valueOf(date);

return sm.format(dt);
$$
  • TO_NUMBER
drop alias if exists TO_NUMBER;
create alias TO_NUMBER as $$
import java.text.*;
@CODE
Long toNumber(String ... values) throws Exception {
  return Long.decode(values[0]);
}
$$
© 2009-2017 Osajiru All Rights Reserved.