java spring rest spring-boot timeout

java - Spring Boot REST API-¿Tiempo de espera de solicitud?



spring-boot timeout (6)

En los archivos de propiedades de Spring, no puede simplemente especificar un número para esta propiedad. También necesita especificar una unidad. Entonces puede decir spring.mvc.async.request-timeout=5000ms o spring.mvc.async.request-timeout=5s , los cuales le darán un tiempo de espera de 5 segundos.

Tengo un servicio Spring Boot REST que a veces llama a servicios de terceros como parte de una solicitud. Me gustaría establecer un tiempo de espera en todos mis recursos (digamos 5 segundos), de modo que si el manejo de una solicitud (toda la cadena, desde la entrada hasta la respuesta) demora más de 5 segundos, mis controladores responden con HTTP 503 en lugar de la respuesta real . Sería increíble si esto fuera solo una propiedad de Spring, por ejemplo, la configuración

spring.mvc.async.request-timeout=5000

Pero no he tenido suerte con eso. También he intentado extender WebMvcConfigurationSupport y anular configureAsyncSupport:

@Override public void configureAsyncSupport(final AsyncSupportConfigurer configurer) { configurer.setDefaultTimeout(5000); configurer.registerCallableInterceptors(timeoutInterceptor()); } @Bean public TimeoutCallableProcessingInterceptor timeoutInterceptor() { return new TimeoutCallableProcessingInterceptor(); }

Sin suerte.

Sospecho que tengo que cronometrar manualmente todas mis llamadas de terceros, y si tardan demasiado, lanzar una excepción de tiempo de espera. ¿Está bien? ¿O hay alguna solución holística más fácil que cubra todos mis puntos finales de solicitud?


La anotación @Transactional toma un parámetro de tiempo de espera en el que puede especificar el tiempo de espera en segundos para un método específico en @RestController

@RequestMapping(value = "/method", method = RequestMethod.POST, produces = MediaType.APPLICATION_JSON_VALUE) @Timed @Transactional(timeout = 120)


Le sugiero que eche un vistazo al arrancador Spring Cloud Netflix Hystrix para manejar llamadas remotas potencialmente poco confiables / lentas. Implementa el patrón de disyuntor, que está destinado precisamente a este tipo de cosas.

Ver documentos oficiales para más información .


Puede probar server.connection-timeout=5000 en su application.properties. De la documentación oficial :

server.connection-timeout = # Tiempo en milisegundos que los conectores esperarán otra solicitud HTTP antes de cerrar la conexión. Cuando no se establece, se usará el valor predeterminado específico del contenedor del conector. Use un valor de -1 para indicar que no hay tiempo de espera (es decir, infinito).

Por otro lado, es posible que desee manejar los tiempos de espera en el lado del cliente utilizando el patrón de disyuntor como ya he descrito en mi respuesta aquí: https://.com/a/44484579/2328781


si está utilizando RestTemplate, debe usar el siguiente código para implementar tiempos de espera

@Bean public RestTemplate restTemplate() { return new RestTemplate(clientHttpRequestFactory()); } private ClientHttpRequestFactory clientHttpRequestFactory() { HttpComponentsClientHttpRequestFactory factory = new HttpComponentsClientHttpRequestFactory(); factory.setReadTimeout(2000); factory.setConnectTimeout(2000); return factory; }}

La configuración xml

<bean class="org.springframework.web.client.RestTemplate"> <constructor-arg> <bean class="org.springframework.http.client.HttpComponentsClientHttpRequestFactory" p:readTimeout="2000" p:connectTimeout="2000" /> </constructor-arg>


Callable<> devolver un Callable<> si desea que spring.mvc.async.request-timeout=5000 funcione.

@RequestMapping(method = RequestMethod.GET) public Callable<String> getFoobar() throws InterruptedException { return new Callable<String>() { @Override public String call() throws Exception { Thread.sleep(8000); //this will cause a timeout return "foobar"; } }; }