Weblogic EJB 통화는 옵션 AldataException을 사용하여 중간 부하에서 실패하기 시작합니다.

StackOverflow https://stackoverflow.com/questions/2454234

문제

당사의 시스템 설정은 두 개의 Weblogic 10.3 서버로 구성됩니다. 하나는 프리젠 테이션 계층을 호스팅하고 다른 하나는 EJB를 호스팅합니다. 시스템은 한동안 중간 부하에서 정상으로 실행되며 (1 ~ 며칠) EJB 메서드가 프리젠 테이션 서버에서 EJB 서버로 호출하여 다음 오류로 실패하기 시작합니다.

java.rmi.RemoteException: java.rmi.UnmarshalException: error unmarshalling arguments; nested exception is: java.io.OptionalDataException

스택 추적 :

java.io.OptionalDataException
    at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1349)
    at java.io.ObjectInputStream.readObject(ObjectInputStream.java:351)
    at weblogic.utils.io.ChunkedObjectInputStream.readObject(ChunkedObjectInputStream.java:197)
    at weblogic.rjvm.MsgAbbrevInputStream.readObject(MsgAbbrevInputStream.java:564)
    at weblogic.utils.io.ChunkedObjectInputStream.readObject(ChunkedObjectInputStream.java:193)
    at weblogic.jndi.internal.RootNamingNode_WLSkel.invoke(Unknown Source)
    at weblogic.rmi.internal.BasicServerRef.invoke(BasicServerRef.java:589)
    at weblogic.rmi.cluster.ClusterableServerRef.invoke(ClusterableServerRef.java:230)
    at weblogic.rmi.internal.BasicServerRef$1.run(BasicServerRef.java:477)
    at weblogic.security.acl.internal.AuthenticatedSubject.doAs(AuthenticatedSubject.java:363)
    at weblogic.security.service.SecurityManager.runAs(Unknown Source)
    at weblogic.rmi.internal.BasicServerRef.handleRequest(BasicServerRef.java:473)
    at weblogic.rmi.internal.wls.WLSExecuteRequest.run(WLSExecuteRequest.java:118)

첫 번째 OptionalDataException이 발생하면 모든 후속 호출이 동일한 결과로 실패합니다. 일부 소스는 이것이 클러스터 멀티 캐스트 포트와 관련이있을 수 있음을 시사합니다. 그러나 이러한 서버는 클러스터에 속하지 않습니다.

EJB 서버를 부팅하면 항상 일시적으로 문제가 해결되지만 문제는 얼마 후에 다시 발생하는 것으로 보입니다.

업데이트: 문제는 것 같습니다 ~ 아니다 결국 소켓 연결 수의 오버플로와 관련이 있습니다 (아래의 답변 참조). 네트워크 클래스로드를 허용하지 않은 후 우리는 일주일 동안 매우 꾸준히 실행 한 후 프레젠테이션 서버에서 옵션 AldataExceptions를 다시 받기 시작했습니다 (아래 스택 추적). 시스템이 일주일 동안 잘 작동하고 실패하기 시작하는 것은 매우 이상합니다.

javax.naming.CommunicationException [Root exception is java.rmi.UnmarshalException: error unmarshalling arguments; nested exception is:
    java.io.OptionalDataException]
    at weblogic.jndi.internal.ExceptionTranslator.toNamingException(ExceptionTranslator.java:74)
    at weblogic.jndi.internal.WLContextImpl.translateException(WLContextImpl.java:439)
    at weblogic.jndi.internal.WLContextImpl.lookup(WLContextImpl.java:395)
    at weblogic.jndi.internal.WLContextImpl.lookup(WLContextImpl.java:380)
    at javax.naming.InitialContext.lookup(InitialContext.java:392)
    ...
Caused by: java.rmi.UnmarshalException: error unmarshalling arguments; nested exception is:

    java.io.OptionalDataException
    at weblogic.rjvm.ResponseImpl.unmarshalReturn(ResponseImpl.java:234)
    at weblogic.rmi.cluster.ClusterableRemoteRef.invoke(ClusterableRemoteRef.java:348)
    at weblogic.rmi.cluster.ClusterableRemoteRef.invoke(ClusterableRemoteRef.java:259)
    at weblogic.jndi.internal.ServerNamingNode_1030_WLStub.lookup(Unknown Source)
    at weblogic.jndi.internal.WLContextImpl.lookup(WLContextImpl.java:392)  
    ... 38 more
Caused by: java.io.OptionalDataException
    at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1349)
    at java.io.ObjectInputStream.readObject(ObjectInputStream.java:351)
    at     
    weblogic.utils.io.ChunkedObjectInputStream.readObject(ChunkedObjectInputStream.java:197)
    at weblogic.rjvm.MsgAbbrevInputStream.readObject(MsgAbbrevInputStream.java:564)
    at     
weblogic.utils.io.ChunkedObjectInputStream.readObject(ChunkedObjectInputStream.java:193)
    at weblogic.jndi.internal.RootNamingNode_WLSkel.invoke(Unknown Source)
    at weblogic.rmi.internal.BasicServerRef.invoke(BasicServerRef.java:589)
    at weblogic.rmi.cluster.ClusterableServerRef.invoke(ClusterableServerRef.java:230)
    at weblogic.rmi.internal.BasicServerRef$1.run(BasicServerRef.java:477)
    at        
weblogic.security.acl.internal.AuthenticatedSubject.doAs(AuthenticatedSubject.java:363)
    at weblogic.security.service.SecurityManager.runAs(Unknown Source)
    at weblogic.rmi.internal.BasicServerRef.handleRequest(BasicServerRef.java:473)
    at weblogic.rmi.internal.wls.WLSExecuteRequest.run(WLSExecuteRequest.java:118)
    ... 2 more

우리는 초기 컨텍스트를 표준 방식으로 얻습니다.

Properties p = new Properties();
p.put(Context.INITIAL_CONTEXT_FACTORY, "weblogic.jndi.WLInitialContextFactory");
p.put(Context.PROVIDER_URL, serverPath);
Context context = new InitialContext(p);

또한 유사한 옵션 AldataException으로 얻은 참조에 대한 호출이 실패합니다. 프레젠테이션 서버 만 부팅하면 문제가 일시적으로 해결됩니다.

도움이 되었습니까?

해결책

마지막으로 옵션 AldataExceptions는 역사입니다. 요컨대, 응용 프로그램 코드에서 복잡한 값 객체 (원격 메소드 호출에 대한 리턴 값으로 사용됨)는 내부 필드로 해시 맵 데이터를 가졌다. 이 필드의 유형을 변경 한 후 옵션 AldataExceptions가 발생하지 않았습니다. 레거시 코드 어딘가에이 맵은 스레드 안전 방식으로 처리 된 것 같습니다.

이상한 점은 WLS 8.1에 문제가 발생하지 않았지만 어떻게 든 WLS 10이 모든 후속 원격 메소드 호출 (JNDI 조회 포함)이 실패하기 시작한 상태에 들어갔습니다.

다른 팁

마지막으로 우리는 이것에 대한 해결책을 찾았습니다 (편집 : 나중에 우리는 이것이 문제의 근본 원인이 아니라 별도의 심각한 문제라는 것을 알았습니다. 최종 해결책은 아래 답변을 참조하십시오). 다음과 같은 예외를 받기 시작하면 원인의 트랙을 얻었습니다.

<BEA-000403> <IOException occurred on socket: Socket[addr=/x.x.x.x,port=3266,localport=7001]
 java.net.SocketException: Connection refused.
java.net.SocketException: Connection refused
at java.net.SocketInputStream.socketRead0(Native Method)
at java.net.SocketInputStream.read(SocketInputStream.java:129)
at weblogic.socket.SocketMuxer.readReadySocketOnce(SocketMuxer.java:887)
at weblogic.socket.SocketMuxer.readReadySocket(SocketMuxer.java:859)
at weblogic.socket.DevPollSocketMuxer.processSockets(DevPollSocketMuxer.java:120)
at weblogic.socket.SocketReaderRequest.run(SocketReaderRequest.java:29)
at weblogic.socket.SocketReaderRequest.execute(SocketReaderRequest.java:42)
at weblogic.kernel.ExecuteThread.execute(ExecuteThread.java:145)
at weblogic.kernel.ExecuteThread.run(ExecuteThread.java:117)

EJB 서버와 다른 호스트에서 실행중인 프레젠테이션 서버에서 옵션이 있습니다.

-Dweblogic.NetworkClassLoadingEnabled=true

EJB 서버에서 클래스로드를 분명히 활성화합니다. 우리가 모르는 것은이 옵션을 사용하면 수많은 네트워크 소켓이 열릴 수 있다는 것입니다. Netstat를 사용하여 수천 개의 소켓이 Close_wait 또는 Fin_Wait_2 상태에 있음을 알 수있었습니다. 프레젠테이션 서버의 전쟁 파일 에이 모든 것이 포함되어 있음에도 불구하고 웹 UI의 모든 요소가 클래스 외에도 EJB 서버에서로드 된 것 같습니다. Weblogic이 시작 스크립트에서 파일의 ulimit을 제거하기 때문에 엄청난 양의 소켓은 "너무 많은 파일"오류 메시지를 초래하지 않았습니다. 테스트 서버를 사용하여 사용자의 웹 UI를 한 번 클릭하면 두 서버 사이에 약 30 개의 소켓이 열렸다는 것을 알았습니다.

우리는이 옵션을 제거하고 프레젠테이션 서버에서 전쟁을 다시 포장하여 필요한 모든 클래스를 포함하여 네트워크 클래스로드가 필요하지 않습니다. 이로 인해 두 서버 간의 소켓 연결 수가 수천에서 1까지 감소했습니다.

요약하면, 가능한 경우 Weblogic의 네트워크 클래스로드를 피하십시오.

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top