2012-02-11 1 views
1

Tomcat에서 제공하는 Java/JSP 웹 응용 프로그램을 사용하여 웹 서비스를 호출하여 파트너 웹 서비스에서 데이터를 검색합니다. 파트너 서비스에 사용 된 기술은 알려져 있지 않습니다. 파트너 웹 서비스가 짧은 정전이있는 경우Tomcat Java 서버 응용 프로그램이 여러 종속 java.net.SocketTimeoutExceptions에서 복구되지 않습니다.

java.net.SocketTimeoutException: connect timed out 
    at java.net.PlainSocketImpl.socketConnect(Native Method) 
    at java.net.PlainSocketImpl.doConnect(Unknown Source) 
    at java.net.PlainSocketImpl.connectToAddress(Unknown Source) 
    at java.net.PlainSocketImpl.connect(Unknown Source) 
    at java.net.Socket.connect(Unknown Source) 
    at sun.net.NetworkClient.doConnect(Unknown Source) 
    at sun.net.www.http.HttpClient.openServer(Unknown Source) 
    at sun.net.www.http.HttpClient.openServer(Unknown Source) 
    at sun.net.www.protocol.https.HttpsClient.<init>(Unknown Source) 
    at sun.net.www.protocol.https.HttpsClient.New(Unknown Source) 
    at sun.net.www.protocol.https.AbstractDelegateHttpsURLConnection.getNewHttpClient(Unknown Source) 
    at sun.net.www.protocol.http.HttpURLConnection.plainConnect(Unknown Source) 
    at sun.net.www.protocol.https.AbstractDelegateHttpsURLConnection.connect(Unknown Source) 
    at sun.net.www.protocol.http.HttpURLConnection.getInputStream(Unknown Source) 
    at sun.net.www.protocol.https.HttpsURLConnectionImpl.getInputStream(Unknown Source) 

, 신속 복구, 내 응용 프로그램이 잘 모든 것을 처리 : 파트너 웹 서비스는 그것이 지정해 SocketTimeoutException을 반환 자주 확장 중단을 가지고있다.

파트너 웹 서비스의 서비스가 한 시간 이상 중단 된 경우 응용 프로그램에 시간이 모두 초과 된 서비스에 대한 수백 건의 호출이 있었는데 어느 시점에서 내 응용 프로그램이 복구되지 않는 상태에 도달했습니다. 파트너 서비스가 다시 돌아 오지만 내 응용 프로그램 호출로 해당 서비스를 호출해도 여전히 정확한 SocketTimeoutException 오류가 발생합니다.

그 시점에서 Tomcat을 시작하고 중지하면 모든 것이 잘 작동합니다.

저는 HTTP 연결 유지를 사용하지 않습니다. 내 코드는 예외가 발생하는지 여부에 관계없이 모든 객체 인스턴스를 정리하는 항문입니다. Tomcat Java 프로세스가 리소스 (소켓)를 "사용"하고있어 더 이상 사용할 수 없을 때까지 각 오류와 함께 하나씩 버리는 것 같습니다. 누구든지 전에 이것을 보았으며 명백한 해결책이 있습니까? 나는이 문제에 대해 많은 조사를 해왔으며 동일한 문제가있는 사람을 찾지 못했다.

미리 감사드립니다. John

+0

시스템이이 쐐기 상태가되면 스택 덤프 또는 힙 덤프를 수행 했습니까? 이들은 잠재적으로 다양한 자원 고갈 문제를 지적 할 수 있습니다. 또한, 바람둥이를 수신 거부하기 전에 컴퓨터에 열려있는 소켓을 나열해야합니다. – jtahlborn

+0

netstat -ano는 실제로 TIME_WAIT 상태에 고정 된 많은 TCP 소켓을 보여줍니다. 이들 대부분의 PID는 0이며 시스템 유휴 프로세스입니다. 그게 무슨 뜻 이죠? – Squidious

답변

0

TCP_WAIT 상태의 연결에 대해 TCP/IP 스택의 슬롯이 부족한 상황이있었습니다. 운영 체제에 부합하는 하드 제한이 있습니다. . 한계가 무엇인지 알아내는 방법은 Windows 서버에서 실행중인 경우 sysinternals의 도구 중 일부를 사용할 수있는 netstat와 같은 도구를 사용하는 것입니다.

문제에 대한 해결책은 서킷 브레이커라는 디자인 패턴 책에서 설명 될 수있는 것입니다 무슨 회로 차단기 패턴 http://pragprog.com/book/mnee/release-it

라고하는 회로 차단기를 통해 원격 웹 서비스 흐름에 통화 차단기가 열린 상태에있을 때 원격 서비스에 너무 많은 호출이 실패하면 차단기가 열립니다. 원격 서비스 호출은 차단기 코드에서 즉시 실패합니다. 대개 차단기를 다시 시도하여 프로그램이 실행되는지 다시 열어. 어쨌든이 책은 제가 여러분에게 준 간단한 설명보다 더 나은 설명을 가지고 있습니다.

https://bitbucket.org/asaikali/circuitbreaker/에는 CircuitBreaker 패턴의 오픈 소스 샘플 구현이 있습니다.

+0

netstat -ano는 실제로 TIME_WAIT 상태에 고정 된 많은 TCP 소켓을 보여줍니다. 이들 대부분의 PID는 0이며 시스템 유휴 프로세스입니다. 그게 무슨 뜻 이죠? – Squidious

+0

여기에 좋은 정보와 제안이 있습니다. http://wiki.apache.org/HttpComponents/FrequentlyAskedConnectionManagementQuestions 구현 된 코드 변경은 'urlConn.setRequestProperty ("Connection", "close");' 다음번 정전 후 코드 변경이 실제 문제인지 여부를 다시 알려 드리겠습니다. – Squidious

+0

이 픽스가 프로덕션에 적용된 이후로 한 번의 큰 정전 만있었습니다. 그러나 정전 1 시간 후에 우리 서버가 훌륭하게 복구되었습니다. 수정 사항이 좋아 보인다. – Squidious

관련 문제