4.3.7. Seam 2.2 Booking アーカイブのランタイムエラーや例外のデバッグおよび解決

前述の手順、「Seam 2.2 Booking アーカイブのデプロイメントエラーや例外のデバッグおよび解決」 ではデプロイメントエラーのデバッグ方法について説明しました。この手順では発生したランタイムエラーをデバッグし解決します。

重要

Seam 2.2 で Hibernate を直接使用するアプリケーションは、アプリケーション内部にパッケージ化された Hibernate 3 のバージョンを使用することがあります。JBoss EAP 6 の org.hibernate モジュールを介して提供される Hibernate 4 は、Seam 2.2 によってサポートされません。この例の目的は、最初の手順として JBoss EAP 6 でアプリケーションを実行させることです。Hibernate 3 を Seam 2.2 アプリケーションでパッケージ化する設定はサポートされないことに注意してください。

手順4.11 ランタイムエラーや例外のデバッグおよび解決

この時点では、アプリケーションをデプロイしてもログにエラーは記録されていませんが、アプリケーション の URL にアクセスするとエラーがログに記録されます。
  1. 問題 - javax.naming.NameNotFoundException: Name 'jboss-seam-booking' not found in context ''
    ブラウザーで URL http://localhost:8080/seam-booking/ にアクセスすると、「The page isn't redirecting properly (ページが正常にリダイレクトされていません)」というメッセージが示され、ログに以下のエラーが記録されます。
    SEVERE [org.jboss.seam.jsf.SeamPhaseListener] (http--127.0.0.1-8080-1) swallowing exception: java.lang.IllegalStateException: Could not start transaction
      at org.jboss.seam.jsf.SeamPhaseListener.begin(SeamPhaseListener.java:598) [jboss-seam.jar:]
      (... log messages removed ...)
    Caused by: org.jboss.seam.InstantiationException: Could not instantiate Seam component: org.jboss.seam.transaction.synchronizations
      at org.jboss.seam.Component.newInstance(Component.java:2170) [jboss-seam.jar:]
      (... log messages removed ...)
    Caused by: javax.naming.NameNotFoundException: Name 'jboss-seam-booking' not found in context ''
      at org.jboss.as.naming.util.NamingUtils.nameNotFoundException(NamingUtils.java:109)
      (... log messages removed ...)
    
    ログの解説

    NameNotFoundException は JNDI の命名の問題であることを示しています。JBoss EAP 6 では JNDI の命名ルールが変更になったため、新しいルールに従ってルックアップ名を変更する必要があります。

    解決方法

    これをデバッグするには、使用された JNDI バインディングに対するサーバーログトレースを確認します。サーバーログを確認すると、内容は以下のようになります。

    15:01:16,138 INFO  [org.jboss.as.ejb3.deployment.processors.EjbJndiBindingsDeploymentUnitProcessor] (MSC service thread 1-1) JNDI bindings for session bean named RegisterAction in deployment unit subdeployment "jboss-seam-booking.jar" of deployment "jboss-seam-booking.ear" are as follows:
      java:global/jboss-seam-booking/jboss-seam-booking.jar/RegisterAction!org.jboss.seam.example.booking.Register
      java:app/jboss-seam-booking.jar/RegisterAction!org.jboss.seam.example.booking.Register
      java:module/RegisterAction!org.jboss.seam.example.booking.Register
      java:global/jboss-seam-booking/jboss-seam-booking.jar/RegisterAction
      java:app/jboss-seam-booking.jar/RegisterAction
      java:module/RegisterAction
      [JNDI bindings continue ...]
    
    ログには、各セッション Bean に対して 1 つずつ合計で 8 つの INFO JNDI バインディング (RegisterAction、BookingListAction、HotelBookingAction、AuthenticatorAction、ChangePasswordAction、HotelSearchingAction、EjbSynchronizations、および TimerServiceDispatcher) がリストされます。新しい JNDI バインディングを使用するよう WAR の lib/components.xml ファイルを変更します。ログで、EJB JNDI バインディングがすべて "java:app/jboss-seam-booking.jar" で始まっていることに注意してください。以下のように core:init 要素を置き換えます。
    <!--     <core:init jndi-pattern="jboss-seam-booking/#{ejbName}/local" debug="true" distributable="false"/> -->
    <core:init jndi-pattern="java:app/jboss-seam-booking.jar/#{ejbName}" debug="true" distributable="false"/>
    
    次に、EjbSynchronizations バインディングと TimerServiceDispatcher JNDI バインディングを追加する必要があります。ファイルに以下のコンポーネント要素を追加します。
    <component class="org.jboss.seam.transaction.EjbSynchronizations" jndi-name="java:app/jboss-seam/EjbSynchronizations"/>
    <component class="org.jboss.seam.async.TimerServiceDispatcher" jndi-name="java:app/jboss-seam/TimerServiceDispatcher"/>
    
    components.xml ファイルは以下のようになるはずです。
    <?xml version="1.0" encoding="UTF-8"?>
    <components xmlns="http://jboss.com/products/seam/components"
      xmlns:core="http://jboss.com/products/seam/core"
      xmlns:security="http://jboss.com/products/seam/security"
      xmlns:transaction="http://jboss.com/products/seam/transaction"
      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      xsi:schemaLocation=
        "http://jboss.com/products/seam/core http://jboss.com/products/seam/core-2.2.xsd
         http://jboss.com/products/seam/transaction http://jboss.com/products/seam/transaction-2.2.xsd
         http://jboss.com/products/seam/security http://jboss.com/products/seam/security-2.2.xsd
         http://jboss.com/products/seam/components http://jboss.com/products/seam/components-2.2.xsd">
    
        <!-- <core:init jndi-pattern="jboss-seam-booking/#{ejbName}/local" debug="true" distributable="false"/> -->
        <core:init jndi-pattern="java:app/jboss-seam-booking.jar/#{ejbName}" debug="true" distributable="false"/>
        <core:manager conversation-timeout="120000"
                      concurrent-request-timeout="500"
                      conversation-id-parameter="cid"/>
        <transaction:ejb-transaction/>
        <security:identity authenticate-method="#{authenticator.authenticate}"/>
        <component class="org.jboss.seam.transaction.EjbSynchronizations"
                jndi-name="java:app/jboss-seam/EjbSynchronizations"/>
        <component class="org.jboss.seam.async.TimerServiceDispatcher"
                jndi-name="java:app/jboss-seam/TimerServiceDispatcher"/>
    </components>
    

    standalone/deployments/jboss-seam-booking.ear.failed ファイルを削除して同じディレクトリーに空の jboss-seam-booking.ear.dodeploy ファイルを作成し、アプリケーションを再デプロイします。
  2. 問題 - エラーが発生せずにアプリケーションがデプロイされ、実行されます。ブラウザーで URL http://localhost:8080/seam-booking/ にアクセスし、ログインしようとすると「Login failed. Transaction failed.」 というメッセージが表示され、ログインに失敗します。サーバーログに次のような例外トレースが記録されるはずです。
    13:36:04,631 WARN  [org.jboss.modules] (http-/127.0.0.1:8080-1) Failed to define class org.jboss.seam.persistence.HibernateSessionProxy in Module "deployment.jboss-seam-booking.ear.jboss-seam.jar:main" from Service Module Loader: java.lang.LinkageError: Failed to link org/jboss/seam/persistence/HibernateSessionProxy (Module "deployment.jboss-seam-booking.ear.jboss-seam.jar:main" from Service Module Loader)
    ....
    Caused by: java.lang.LinkageError: Failed to link org/jboss/seam/persistence/HibernateSessionProxy (Module "deployment.jboss-seam-booking.ear.jboss-seam.jar:main" from Service Module Loader)
    ...
    Caused by: java.lang.NoClassDefFoundError: org/hibernate/engine/SessionImplementor
    	at java.lang.ClassLoader.defineClass1(Native Method) [rt.jar:1.7.0_45]
    ...
    Caused by: java.lang.ClassNotFoundException: org.hibernate.engine.SessionImplementor from [Module "deployment.jboss-seam-booking.ear.jboss-seam.jar:main" from Service Module Loader]
    ...
    
    ログの解説

    ClassNotFoundException は Hibernate ライブラリーがないことを示しています。この場合、hibernate-core.jar が存在しません。

    解決方法

    hibernate-core.jar JAR を EAP5_HOME/seam/lib/ ディレクトリーから jboss-seam-booking.ear/lib ディレクトリーへコピーします。

    standalone/deployments/jboss-seam-booking.ear.failed ファイルを削除して同じディレクトリーに空の jboss-seam-booking.ear.dodeploy ファイルを作成し、アプリケーションを再デプロイします。
  3. 問題 - エラーが発生せずにアプリケーションがデプロイされ、実行されます。ブラウザーで URL http://localhost:8080/seam-booking/ にアクセスすると正常にログインできますが、ホテルを予約しようとすると、例外トレースが記録されます。
    これをデバッグするには、真のエラーを隠している jboss-seam-booking.ear/jboss-seam-booking.war/WEB-INF/lib/jboss-seam-debug.jar を最初に削除します。この時点で、次のエラーが表示されるはずです。
    java.lang.NoClassDefFoundError: org/hibernate/annotations/common/reflection/ReflectionManager
    ログの解説

    NoClassDefFoundError は Hibernate ライブラリーがないことを示しています。

    解決方法

    hibernate-annotations.jar および hibernate-commons-annotations.jar JAR を EAP5_HOME/seam/lib/ ディレクトリーから jboss-seam-booking.ear/lib ディレクトリーへコピーします。

    standalone/deployments/jboss-seam-booking.ear.failed ファイルを削除して同じディレクトリーに空の jboss-seam-booking.ear.dodeploy ファイルを作成し、アプリケーションを再デプロイします。
  4. ランタイムおよびアプリケーションエラーが解決されるはずです。
    この時点で、エラーが発生せずにアプリケーションがデプロイおよび実行されます。
    以前のトピックに戻るには、「Seam 2.2 Booking アーカイブの JBoss EAP 6 への移行: 手順説明」をクリックしてください。