본문 바로가기
IBM - old/WAS 문제&해결

EJB 호출시(remote call) stub 관련 ClassCastException

by freeman98 2016. 5. 6.

1. WAS 버전 : WebSphere ND v7.0.0.7

2. OS : All

3. Error 발생 시점 :  다른 어플리케이션에 있는 EJB 를 remote 방식으로 호출시

4. Error message :
[10. 1. 7   13:31:11:921 KST] 00000013 servlet       E com.ibm.ws.webcontainer.servlet.ServletWrapper service SRVE0068E: EJBCallTestEAR 응용프로그램에 있는 Servlet EJBCallerServlet의 서비스 메소드 중 하나에서 미발견 예외가 작성되었습니다. 작성된 예외: java.lang.ClassCastException: com.ibm.juwlee.ejb._EJBCalleeBeanRemote_Stub incompatible with com.ibm.juwlee.ejb.EJBCalleeBeanRemote
    at com.ibm.juwlee.servlet.EJBCallerServlet.remoteCall(EJBCallerServlet.java:58)
    at com.ibm.juwlee.servlet.EJBCallerServlet.doGet(EJBCallerServlet.java:39)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:718)
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:831)
    at com.ibm.ws.webcontainer.servlet.ServletWrapper.service(ServletWrapper.java:1583)
    at com.ibm.ws.webcontainer.servlet.ServletWrapper.handleRequest(ServletWrapper.java:870)
    at com.ibm.ws.webcontainer.servlet.ServletWrapper.handleRequest(ServletWrapper.java:475)
    at com.ibm.ws.webcontainer.servlet.ServletWrapperImpl.handleRequest(ServletWrapperImpl.java:175)
    at com.ibm.ws.webcontainer.webapp.WebApp.handleRequest(WebApp.java:3799)
    at com.ibm.ws.webcontainer.webapp.WebGroup.handleRequest(WebGroup.java:276)
    at com.ibm.ws.webcontainer.WebContainer.handleRequest(WebContainer.java:930)
    at com.ibm.ws.webcontainer.WSWebContainer.handleRequest(WSWebContainer.java:1583)
    at com.ibm.ws.webcontainer.channel.WCChannelLink.ready(WCChannelLink.java:182)
    at com.ibm.ws.http.channel.inbound.impl.HttpInboundLink.handleDiscrimination(HttpInboundLink.java:455)
    at com.ibm.ws.http.channel.inbound.impl.HttpInboundLink.handleNewInformation(HttpInboundLink.java:384)
    at com.ibm.ws.http.channel.inbound.impl.HttpInboundLink.ready(HttpInboundLink.java:272)
    at com.ibm.ws.tcp.channel.impl.NewConnectionInitialReadCallback.sendToDiscriminators(NewConnectionInitialReadCallback.java:214)
    at com.ibm.ws.tcp.channel.impl.NewConnectionInitialReadCallback.complete(NewConnectionInitialReadCallback.java:113)
    at com.ibm.ws.tcp.channel.impl.AioReadCompletionListener.futureCompleted(AioReadCompletionListener.java:165)
    at com.ibm.io.async.AbstractAsyncFuture.invokeCallback(AbstractAsyncFuture.java:217)
    at com.ibm.io.async.AsyncChannelFuture.fireCompletionActions(AsyncChannelFuture.java:161)
    at com.ibm.io.async.AsyncFuture.completed(AsyncFuture.java:138)
    at com.ibm.io.async.ResultHandler.complete(ResultHandler.java:204)
    at com.ibm.io.async.ResultHandler.runEventProcessingLoop(ResultHandler.java:775)
    at com.ibm.io.async.ResultHandler$2.run(ResultHandler.java:905)
    at com.ibm.ws.util.ThreadPool$Worker.run(ThreadPool.java:1550)

5. 예상 이유 :
 EJB 3.0 부터는 EJB call 에 필요한 stub 을 사전에 만드는 것이 아니라 불리워지는 EJB 에게서 자동으로 받아옵니다.
 이렇게 받아온 Stub 을 그냥 캐스팅 방식으로 형변환을 하게 되면 incompatible 하다며 ClassCastException 이 발생합니다.
 ejb3RemoteSession = (EJBCalleeBeanRemote) new InitialContext().lookup("ejb/com.ibm.juwlee.ejb.EJBCalleeBeanRemote");

6. 조치 방안 :
 local call 을 한 경우나 remote call 이라도 같은 어플리케이션에 있는 EJB를 호출하는 경우에는 stub 에 대하여 단순 캐스팅
 방식으로 형변환이 가능합니다. 그러나 다른 어플리케이션에 있는 EJB를 remote 로 호출하는 경우에는 반드시
 RMI 에서 지정한 방식으로 하단처럼 narrow 를 해주어야 합니다.
 ejb3RemoteSession = (EJBCalleeBeanRemote) javax.rmi.PortableRemoteObject.narrow(new InitialContext().lookup("ejb/com.ibm.juwlee.ejb.EJBCalleeBeanRemote
"), EJBCalleeBeanRemote.class );

댓글