Cayenne
Cayenneとは
標準で付属されているCayenneModelerというGUIツールを利用してデータベースアクセス部分のソースコードを自動生成する点が特徴。
O/Rデータベースマッピングフレームワーク
オブジェクト指向とリレーショナルデータベースを用いてシステムを開発すると、インピーダンス・ミスマッチ(Impedance Mismatch)と呼ばれるギャップが発生する。これはオブジェクト指向とリレーショナルデータベースとの考え方が異なるためである。
O/Rマッピングフレームワークとは、このギャップを軽減するためのフレームワークのことで、O/RのOはオブジェクト、Rはリレーショナルを意味している。
入手
マッピング
CayenneModelerの利用方法はオフィシャルサイトのCayenneModeler Guideを参照。画像付き。
http://www.objectstyle.org/cayenne/modelerguide/index.html
検索
全レコード検索
import java.util.Iterator;
import java.util.List;
import org.objectstyle.cayenne.access.DataContext;
import org.objectstyle.cayenne.query.SelectQuery;
public class SelectAllEmp {
public static void main(String[] args) {
DataContext dataContext = DataContext.createDataContext();
SelectQuery selectQuery = new SelectQuery(Emp.class);
List list = dataContext.performQuery(selectQuery);
Iterator iterator = list.iterator();
while(iterator.hasNext()){
Emp emp = (Emp)iterator.next();
System.out.println(emp.getEname());
}
}
}
DataContext…データの取得、保存などの中心的な処理を実行するクラス。取得方法はいくつかあり、対応するデータベースの数などによって異なるが、上記の方法が一番簡単。
いろいろな条件検索
where ename=’SMITH’
Expression expression = ExpressionFactory.matchExp("ename", "SMITH");
SelectQuery query = new SelectQuery(Emp.class, expression);
where job = ‘SALESMAN’ and comm <> 0
Expression expression = ExpressionFactory.matchExp("job", "SALESMAN");
expression = expression.andExp(ExpressionFactory.matchExp("comm", new BigDecimal(0)));
SelectQuery query = new SelectQuery(Emp.class, expression);
where ename = ‘SMITH’ or ename=’WARD’
Expression expression = ExpressionFactory.matchExp("ename", "SMITH");
expression = expression.orExp(ExpressionFactory.matchExp("ename", "WARD"));
SelectQuery query = new SelectQuery(Emp.class, expression);
where ename <> ‘SMITH’ and ename <> ‘WARD’
Expression expression = ExpressionFactory.noMatchExp("ename", "SMITH");
expression = expression.andExp(ExpressionFactory.noMatchExp("ename", "WARD"));
SelectQuery query = new SelectQuery(Emp.class, expression);
where sal > 1500
Expression expression = ExpressionFactory.greaterExp("sal", new BigDecimal(1500));
SelectQuery query = new SelectQuery(Emp.class, expression);
where sal >= 1500
Expression expression = ExpressionFactory.greaterOrEqualExp("sal", new BigDecimal(1500));
SelectQuery query = new SelectQuery(Emp.class, expression);
where sal < 1500
Expression expression = ExpressionFactory.lessExp("sal", new BigDecimal(1500));
SelectQuery query = new SelectQuery(Emp.class, expression);
where sal <= 1500
Expression expression = ExpressionFactory.lessOrEqualExp("sal", new BigDecimal(1500));
SelectQuery query = new SelectQuery(Emp.class, expression);
where ename in (‘SMITH’, ‘WARD’)
List empList = new ArrayList();
empList.add("SMITH");
empList.add("WARD");
Expression expression = ExpressionFactory.inExp("ename", empList);
SelectQuery query = new SelectQuery(Emp.class, expression);
where ename not in (‘SMITH’, ‘WARD’)
List empList = new ArrayList();
empList.add("SMITH");
empList.add("WARD");
Expression expression = ExpressionFactory.notInExp("ename", empList);
SelectQuery query = new SelectQuery(Emp.class, expression);
where ename like ‘A%’
Expression expression = ExpressionFactory.likeExp("ename", "A%");
SelectQuery query = new SelectQuery(Emp.class, expression);
where ename not like ‘A%’
Expression expression = ExpressionFactory.notLikeExp("ename", "A%");
SelectQuery query = new SelectQuery(Emp.class, expression);
where sal betwheen 1500 and 1800
Expression expression = ExpressionFactory.betweenExp("sal", new BigDecimal(1500), new BigDecimal(1800));
SelectQuery query = new SelectQuery(Emp.class, expression);
where sal not betwheen 1500 and 1800
Expression expression = ExpressionFactory.notBetweenExp("sal", new BigDecimal(1500), new BigDecimal(1800));
SelectQuery query = new SelectQuery(Emp.class, expression);
※上記のような書式以外にも、下記のような方法で条件を指定することも可能。
Expression expression1 = ExpressionFactory.matchExp("ename", "SMITH");
Expression expression2 = ExpressionFactory.matchExp("ename", "WARD");
SelectQuery selectQuery = new SelectQuery(Emp.class);
selectQuery.setQualifier(expression1);
selectQuery.orQualifier(expression2);
ソート
SelectQuery selectQuery = new SelectQuery(Emp.class);
selectQuery.addOrdering("ename", Ordering.ASC);
org.objectstyle.cayenne.query.Orderingクラスの定数を利用する。
ASCで昇順、DESCで降順。
最大検索件数(検索結果の上限)
SelectQuery selectQuery = new SelectQuery(Emp.class); selectQuery.setFetchLimit(5);
結果のキャッシュ
SelectQuery selectQuery = new SelectQuery(Emp.class); selectQuery.setCachePolicy(GenericSelectQuery.NO_CACHE);
org.objectstyle.cayenne.query.GenericSelectQueryクラスの定数を利用する。
指定可能キャッシュタイプ一覧
| 定数 | 意味 |
|---|---|
| GenericSelectQuery.NO_CACHE | キャッシュを利用しない |
| GenericSelectQuery.CACHE_POLICY_DEFAULT | キャッシュを利用しない |
| GenericSelectQuery.CACHE_POLICY_PROPERTY | プロパティの項目cayenne.GenericSelectQuery.cachePolicyを読み込む |
| GenericSelectQuery.LOCAL_CACHE | ローカルにキャッシュを格納 |
| GenericSelectQuery.SHARED_CACHE | 共有できるようにキャッシュを格納 |
関連するデータの取得
関連先が、1レコードの場合
CayenneModelerで外部キーの設定をしておくと、getToXXXというメソッドが自動生成されているので利用する。
Emp emp = ...; Dept dept = emp.getToDept();
関連先が、複数レコードの場合
CayenneModelerで外部キーの設定をしておくと、getXXXArrayというメソッドが自動生成されているので利用する。
Dept dept = ...; List empList = dept.getEmpArray();
レコードの更新
import java.math.BigDecimal;
import java.util.Iterator;
import java.util.List;
import org.objectstyle.cayenne.access.DataContext;
import org.objectstyle.cayenne.exp.Expression;
import org.objectstyle.cayenne.exp.ExpressionFactory;
import org.objectstyle.cayenne.query.SelectQuery;
public class SelectEmpSmith {
public static void main(String[] args) {
DataContext dataContext = DataContext.createDataContext();
Expression expression = ExpressionFactory.matchExp("job", "SALESMAN");
SelectQuery query = new SelectQuery(Emp.class, expression);
List list = dataContext.performQuery(query);
Iterator iterator = list.iterator();
while(iterator.hasNext()) {
Emp emp = (Emp)iterator.next();
emp.setSal(emp.getSal().add(new BigDecimal(10000)));
}
dataContext.commitChanges();
}
}
上記のコード
- JobがSALESMANのレコードを取得
- 現在のSalに10000を加算
- コミット
レコードの挿入
import java.math.BigDecimal;
import org.objectstyle.cayenne.ObjectId;
import org.objectstyle.cayenne.access.DataContext;
public class SelectEmpSmith {
public static void main(String[] args) {
DataContext dataContext = DataContext.createDataContext();
Emp emp = (Emp)dataContext.createAndRegisterNewObject(Emp.class);
emp.setObjectId(new ObjectId(Emp.class, _Emp.EMPNO_PK_COLUMN, new BigDecimal(9999)));
emp.setEname("NEWBE");
emp.setSal(new BigDecimal(50000));
dataContext.commitChanges();
}
}
ObjectIdはレコードのキーを表すクラス。
レコードの削除
import java.math.BigDecimal;
import java.util.Iterator;
import java.util.List;
import org.objectstyle.cayenne.access.DataContext;
import org.objectstyle.cayenne.exp.Expression;
import org.objectstyle.cayenne.exp.ExpressionFactory;
import org.objectstyle.cayenne.query.SelectQuery;
public class SelectAllEmp {
public static void main(String[] args) {
DataContext dataContext = DataContext.createDataContext();
Expression expression = ExpressionFactory.matchExp("ename", "SMITH");
SelectQuery selectQuery = new SelectQuery(Emp.class, expression);
List list = dataContext.performQuery(selectQuery);
Iterator iterator = list.iterator();
while(iterator.hasNext()){
Emp emp = (Emp)iterator.next();
dataContext.deleteObject(emp);
}
dataContext.commitChanges();
}
}
トランザクション
dataContext.commitChanges(); dataContext.commitChanges(org.apache.log4j.Level.DEBUG);
ログレベル指定でトランザクションの内容や実行されるSQL文の出力を制御することができる。
ロールバック
dataContext.rollbackChanges();

