外注したアプリケーションを自社で直せないかという話が持ち上がり、調査している中で手こずった部分があったのでメモ。記憶に頼って書いている部分があるのでバージョン等は前後する可能性あり。これで助かる人はいないかもしれないけど。
元の環境
Interstage Application Server V9 = GlassFish 2.x 相当 + Toplink Essentials (JPA実装)
移行先の環境
GlassFish 3.x - 4.x (JPA実装は、EclipseLink、JPA2.0相当?)
開発環境
Windows 7 + Pleiades (Eclipse 4.4) + Oracle Enterprise Pack for Eclipse 12.1.3.8
EAR の構造
hoge_ear
L dao.jar (Persistence.xml あり)
L その他の jar (EJB等)
:
L web.war (フロントエンド部分)
始めの一歩
GlassFish の準備
基本 Web インターフェースの管理コンソールはあまり使わず。以下、GlassFish の管理コマンド asadmin のサブコマンドを併記しているが、引数等は省略。asadmin help サブコマンド
とかで確認されたし。
- GlassFish の配置
- 環境変数 AS_JAVA の設定(先に Pleiades を展開していれば、同梱の JRE を指定する。)
- GlassFish の起動
asadmin start-domain
- JDBC ドライバを domain の lib ディレクトリに配置
asadmin add-library
- JDBC Connection Pool の追加
asadmin create-jdbc-connection-pool
- 5 で追加した接続が大丈夫か確認
asadmin ping-connection-pool
- JDBC Resource の追加
asadmin create-jdbc-resource
- GlassFish の停止
asadmin stop-domain
Pleiades の準備
- Pleiades の配置
- oepe を展開し、フォルダ plugins,features を 2 の同一名フォルダに統合
- eclipse を起動し、パースフェクティブを JavaEE に変更
- JRE を java8 から java7 に変更(必須ではないが、GlassFish 3.x では問題起こすかも)
- サーバービューでサーバーを追加(GlassFish 3.1.2 で GlassFish 4.x に対応)
- 該当 EAR をインポートし、ビルドパスなどを修正
困ったこと
デプロイ自体は難なく行えたが、実際にログインを行おうとするとそんなユーザ知らねえよと拒否された。該当する GlassFish domain の server.log を確認すると以下のエラーになっていた。
Unable to retrieve EntityManagerFactory for unitName null
当初は、@PersistenceContext
で unitName が明示されていないのがダメなのかと思ったが(素人考え)、明示しても null の部分が変わるだけであった。
JPA 自体が使えるのかどうか、簡単な動的Webアプリケーションを作成したりして、切り分けをした。
解決への導き
いろいろ検索してみたけど、そのものズバリの答えにはたどりつかず。
Java Persistence API (JPA) 実践入門(ひだまりソケットは壊れない)
にて「永続ユニット (Persistence Unit) のパッケージング」の項にある
Java EE 環境における永続ユニットのルートは、次のどれかでなければなりません:
- EJB-JAR ファイル
- WAR ファイルの WEB-INF/classes ディレクトリ
- WAR ファイルの WEB-INF/lib ディレクトリ内の jar ファイル
- EAR ライブラリディレクトリ内の jar ファイル
- アプリケーションクライアント jar ファイル
という記述から、EAR 内における dao.jar (仮)の配備位置が悪いという仮説を立てました。
行なった変更
デプロイメント記述子の中で単純に dao.jar を Library Directory : lib
にドラッグ&ドロップするとデプロイすら失敗した。(なんて乱暴)
- 新たに「JPAプロジェクト」を作成し、EARに追加。(ちゃんと
Library Directory : lib
に配備される。) - dao.jar の persistence.xml を参考に設定。元のは削除。
- dao.jar から Entity クラスを移動してくる。(正確にはコピー&貼り付けして削除)
- ear をデプロイ
これでログインしてその後の操作も問題なく行えるようになりました。(比較的、幸運な例かもしれません。)
雑感
- 以上の説明はかなり行間を読め、みたいな記述になっていて申し訳ない…
- 正直、Java がこんなに普及するとは思ってなかった…(先見の明なし…)
- DI とか CDI のおかげで書くコードの量が格段に減るよね…
- JPA というか O/R マッピング使うと楽だね。データベースサーバの移行も比較的楽そう。
- JavaSE と JavaEE を単なる Edition の違いと考えちゃダメ。JavaEA とかにしたら良かったのに…(< 英語ダメな人)