Ошибка подключения к восходящему каналу или отключение / сброс перед заголовками. причина сброса: разрыв соединения при использовании Spring Boot - PullRequest
1 голос
/ 27 апреля 2020

Я использую Spring Boot с Embedded Tomcat 9.0.36. Это используется как Docker изображение в Kubernetes. Недавно после обновления посланника я начал получать исключения.

  "upstream connect error or disconnect/reset before headers. reset reason: connection termination" with 503 status code

Некоторые люди предлагали увеличить время ожидания простоя до 60 секунд, но при весенней загрузке мне удалось выяснить "Время ожидания соединения" и "Сохранить Alive Time Out ". Я увеличил их до 5 минут, используя приведенный ниже код.

@Configuration
public class TomcatCustomizer implements WebServerFactoryCustomizer<TomcatServletWebServerFactory> {

    private static final Logger LOGGER = LoggerFactory.getLogger(TomcatCustomizer.class);

    @Override
    public void customize(TomcatServletWebServerFactory factory) {

        factory.addConnectorCustomizers(connector -> {
            AbstractHttp11Protocol protocol = (AbstractHttp11Protocol) connector.getProtocolHandler();
            //Setting up connection time out
            protocol.setKeepAliveTimeout(360000);
            protocol.setConnectionTimeout(360000);
            protocol.setMaxKeepAliveRequests(120);
        });
    }
}

Тем не менее, я получаю ту же ошибку. Это приложение вызывает другую внутреннюю службу, которая также находится в Kubernetes. Я могу видеть успешный ответ в своем сервисе, но после этого я не вижу никаких журналов.

1 Ответ

1 голос
/ 29 апреля 2020

Я провел неделю, анализируя это с точки зрения приложения. Я выполнил несколько шагов, предложенных Ops Team.

  • Увеличьте время ожидания на сервере Tomcat до 60 секунд, потому что они настроили то же самое в Envoy
  • Я увеличил время, но не удалось решить проблему.
  • Я использовал Spring Cloud Gateway для службы шлюза. Я подумал, что это проблема, поэтому я изменил ее на шаблоны отдыха, но это также не решило проблему.
  • К счастью, API-интерфейсы проверки работоспособности работают нормально, за исключением тех, которые внутренне связывались с другими службами. В API Здоровья они также общались с другими службами, чтобы проверить свое Здоровье, но я не отвечал напрямую. Я обернул тело ответа, модифицировав его, и ден перенаправил его в пользовательский интерфейс. Я также применил то же самое и использую приведенный ниже код, который вы можете легко понять. Я создал новый объект ответа и удалил все заголовки, которые я получил от внутренних API-интерфейсов и вернулся в пользовательский интерфейс. Это работает как шарм.

//Earlier (Forwarding same headers received from internal service to UI)
ResponseEntity responseEntity = //Received by calling other APIs;
return responseEntity;

//Now (Dropped headers)
ResponseEntity responseEntity = //Received by calling other APIs;
MultiValueMap<String, String> newHeaders = new LinkedMultiValueMap<>();          
if (Objects.nonNull(responseEntity) && Objects.nonNull(responseEntity.getBody())) {
    newHeaders.set("Content-type", responseEntity.getHeaders().getContentType().toString());
    return new ResponseEntity(responseEntity.getBody(), newHeaders, responseEntity.getStatusCode());
}
...