ストアドプロシージャで開いたカーソル(REF CURSOR)をJPA経由で受け取るサンプル。
実行対象のプロシージャ
パラメータは1つで、アウトパラメータでカーソルを返す。CREATE OR REPLACE PROCEDURE REF_CURSOR_TEST(cur out SYS_REFCURSOR)
AS
BEGIN
OPEN CUR FOR SELECT *
FROM USERS;
END;
実行例
EntityManagerのcreateStoredProcedureQueryにストアドプロシージャ名を指定してStoredProcedureQueryを生成します。第2引数には、REF CURSORを受け取るEntityクラスを指定します。(Entity以外でもいいのか?)
executeでストアドプロシージャを実行して、getOutputParameterValueを呼び出してREF CURSORの結果を受け取ります。
ここで受け取ったEntityは管理対象となるので、状態を変更した場合は永続化層に反映される。
final StoredProcedureQuery query = em.createStoredProcedureQuery("REF_CURSOR_TEST", User.class)
.registerStoredProcedureParameter(1, void.class, ParameterMode.REF_CURSOR);
query.execute();
List users = (List) query.getOutputParameterValue(1);
System.out.println("取得件数 = " + users.size());
users.forEach(user -> {
System.out.println("id = " + user.getId());
System.out.println("name = " + user.getName());
user.setName(user.getName() + ":" + user.getId());
}
);
実行結果
ストアドプロシージャで開いたカーソルの結果が受け取れていることがわかる。[EL Fine]: sql: 2015-03-07 23:51:33.88--ClientSession(1620989914)--Connection(108049354)--Thread(Thread[main,5,main])--BEGIN REF_CURSOR_TEST(?); END; bind => [=> 1] 取得件数 = 2 id = 1 name = hoge id = 2 name = fuga