본문 바로가기

개발중/Spring

SocketException의 수수께끼: 첫 번째 API 호출에서만 왜 실패할까? ( retrofit java.net.socketexception connection reset )

728x90
반응형

 

 

우리 프로젝트에 내가 Retrofit 설정을 했는데, 이상한 현상 (?) 이 나타났다.

 

 

 

 

프론트 개발자분께서 이슈를 전달해주기를 아래와 같이 ...

컴퓨터를 껏다가 키고 최초로 웹 프로젝트를 기동시 아래와 같은 에러가 나요.
근데 2, 3, 4 ... 번째는 이런 에러가 안나요. !!!!!!!!! 😡

 

 

 

 

참고로 java.net.SocketException: Connection reset by peer 이라는 예외는 네트워크 연결 중에 원격 피어(peer)가 연결을 강제로 닫았음을 나타냅니다.

 

의심할 수 있는 상황은 아래의 상황들이었습니다.

 

   의심해볼 만한 사항    테스트 결과
      원격 서버가 과부하 상태거나 다운되어 있음        개발 서버이고 부하 상태가 전혀 없었기 때문에 제외
       네트워크 이슈가 발생하여 데이터 전송이 중단됨        네트워크 이슈 일 수도 ? 하지만 왜 첫번째만 안되는가 ?
       원격 서버에서 클라이언트의 연결을 거부함 
       (예: 방화벽, 로드 밸런서 등이 연결을 끊음)
       그럼 두번째 세번째는 왜 커넥션이 되는가 ?

 

아무튼 내가 맞딱드린 이슈는 나름 황당한 이슈이기 때문에 당황스러워서 컴퓨터를 10번 이상 껐다 켰지만 ( ? ) 커넥션이 왜 컴퓨터 껏다 킨 시점으로 최초 1번만 이런 에러가 나는지에 대해 ,,,,, 알 수 없었습니다. 

 

혹시나 이런적 있거나 이유를 아시면 꼭 알려주십쇼 ,,

 

 

 

 

정말 많은 고민 끝에 (?) 아래와 같은 방법으로 해결을 했습니다.

( 혹시나 진짜 정석 해결 방안, 원인을 아시면 꼭 알려주십쇼 🤥 )

 

재시도 로직 구현


네트워크 요청이 실패할 경우 자동으로 재시도하는 로직을 구현할 수 있습니다.

재시도 로직은 일시적인 네트워크 문제를 자동으로 복구할 수 있도록 도와줍니다.

 

 

/**
 * Retrofit 사용해서 API 호출시, SocketException 발생시 재시도
 */
Interceptor connectionInterceptor = chain -> {

    final int maxRetry = 5;
    final long retryInterval = 100;
    int tryCount = 0;

    Request request = chain.request();
    Response response = null;
    SocketException exception = null;

    while (tryCount < maxRetry && (response == null || !response.isSuccessful())) {
        try {
            response = chain.proceed(request);
            if (response.isSuccessful()) {
                return response;
            }
        } catch (SocketException e) {
            log.error("Request failed. {} try , recall api url", tryCount);
            e.printStackTrace();
            exception = e;
        }

        tryCount++;

        if (tryCount < maxRetry) {
            try {
                Thread.sleep(retryInterval);
            } catch (InterruptedException e) {
                Thread.currentThread().interrupt();
            }
        }
    }

    if (exception != null && response == null) {
        throw exception;
    }

    return response;
};

 

 

그래서 컴퓨터 껏다 켰을 때 최초에는 SocketException 가 발생하기 때문에 (?) 이 로직이 참 쓸모 있지만

tryCount 의 값이 최초에 1이 되어 재시도 되지만 그 이후에는 잘 통신되기 때문에 항상 0 이다.

 

( 결국 최초에만 쓸모있는 코드다 .. ;; )

 

 

 

 

완전히 이해한 것이 아니라 찝찝하지만 ... 그래도 해결은 되었으니, 근데 진짜 왜그럴까 ?

 

 

728x90
반응형