2015-05-26 17 views
12

Dịch vụ ủy quyền của tôi trả về http 204 thành công và http 401 thất bại nhưng không có responseBody. Tôi không thể tiêu thụ điều này với máy khách RestTemplate. Nó không cố gắng serialize phản ứng. Các lỗi từ Jackson đề nghị mà tôi bật FAIL_ON_EMPTY_BEANS trong serializer, nhưng làm thế nào để thiết lập này trong restTemplateCách xử lý phản hồi trống trong Spring RestTemplate

Các khách hàng tiêu thụ các api còn lại

@SuppressWarnings("rawtypes") 
@Override 
public boolean preHandle(HttpServletRequest request, HttpServletResponse response, Object handler) throws Exception { 

    RestTemplate restTemplate = new RestTemplate(); 
    System.out.println("\n\n\n\n ============API REQUEST INTERCEPTOR=============== \n\n\n\n\n"); 

    if(StringUtils.isBlank(request.getHeader(AuthenticationKeys.AUTHENTICATIONTOKEN.name().toLowerCase()))){ 
     //TODO AUTHORIZE TOKEN 
     ResponseEntity<AuthenticationResponse> authenticateResponse = restTemplate.getForEntity(authenticateUrl, AuthenticationResponse.class); 
     if(authenticateResponse.getStatusCode().is2xxSuccessful()){ 
      //TODO SET THE TOKEN IN THE CONTEXT 
      return true; 
     }else{ 
      //TODO DO SOME ERROR HANDLING 
      return false; 
     } 
    }else{ 
     AuthorizationRequest authorizationRequest = new AuthorizationRequest(); 
     authorizationRequest.setToken("TESTNG"); 
     ResponseEntity<Object> authorizationResponse = restTemplate.postForEntity(authorizeUrl, request, Object.class); 
     if(authorizationResponse.getStatusCode().is2xxSuccessful()){ 
      return true; 
     }else{ 
      //TODO DO SOME ERROR HANDLING 
      if(authorizationResponse.getStatusCode().equals(HttpStatus.UNAUTHORIZED)){ 
       response.sendError(HttpServletResponse.SC_UNAUTHORIZED, "Oops! access to this API is not authorized to you."); 
      } 
      return false; 
     } 
    } 

các dịch vụ còn lại

@RequestMapping(value="/authorize", method = RequestMethod.POST) 
    void authorize(@RequestBody @Valid AuthorizationRequest request, HttpServletResponse response){ 
     if(request.getToken().equals("TESTING")){ 
      response.setStatus(HttpServletResponse.SC_NO_CONTENT); 
     }else{ 
      response.setStatus(HttpServletResponse.SC_UNAUTHORIZED); 
     } 
    } 
} 

Ngoại lệ

Caused by: com.fasterxml.jackson.databind.JsonMappingException: No serializer found for class org.apache.catalina.connector.CoyoteInputStream and no properties discovered to create BeanSerializer (to avoid exception, disable SerializationFeature.FAIL_ON_EMPTY_BEANS)) (through reference chain: org.apache.shiro.web.servlet.ShiroHttpServletRequest["request"]->org.apache.catalina.connector.RequestFacade["inputStream"]) 
    at com.fasterxml.jackson.databind.ser.impl.UnknownSerializer.failForEmpty(UnknownSerializer.java:59) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.impl.UnknownSerializer.serialize(UnknownSerializer.java:26) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:575) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:663) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:156) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:575) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:663) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:156) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.DefaultSerializerProvider.serializeValue(DefaultSerializerProvider.java:129) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ObjectMapper.writeValue(ObjectMapper.java:2238) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.writeInternal(AbstractJackson2HttpMessageConverter.java:231) ~[spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    ... 52 more 

Các Cố gắng Fix

RestTemplate restTemplate = new RestTemplate(); 
     List<HttpMessageConverter<?>> converters = restTemplate.getMessageConverters(); 
     for(HttpMessageConverter<?> converter : converters){ 
      if(converter instanceof MappingJackson2HttpMessageConverter){ 
       ((MappingJackson2HttpMessageConverter) converter).getObjectMapper().configure(SerializationFeature.FAIL_ON_EMPTY_BEANS, false); 
      } 
     } 

Lỗi tiếp theo

org.springframework.http.converter.HttpMessageNotWritableException: Could not write content: getInputStream() has already been called for this request (through reference chain: org.apache.shiro.web.servlet.ShiroHttpServletRequest["request"]->org.apache.catalina.connector.RequestFacade["reader"]); nested exception is com.fasterxml.jackson.databind.JsonMappingException: getInputStream() has already been called for this request (through reference chain: org.apache.shiro.web.servlet.ShiroHttpServletRequest["request"]->org.apache.catalina.connector.RequestFacade["reader"]) 
    at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.writeInternal(AbstractJackson2HttpMessageConverter.java:238) ~[spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.springframework.http.converter.AbstractHttpMessageConverter.write(AbstractHttpMessageConverter.java:208) ~[spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.springframework.web.client.RestTemplate$HttpEntityRequestCallback.doWithRequest(RestTemplate.java:777) ~[spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.springframework.web.client.RestTemplate.doExecute(RestTemplate.java:566) ~[spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.springframework.web.client.RestTemplate.execute(RestTemplate.java:529) ~[spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.springframework.web.client.RestTemplate.postForEntity(RestTemplate.java:356) ~[spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at mordeth.orchestration.interceptor.ApiRequestInterceptor.preHandle(ApiRequestInterceptor.java:120) ~[ApiRequestInterceptor.class:?] 
    at org.springframework.web.servlet.HandlerExecutionChain.applyPreHandle(HandlerExecutionChain.java:134) ~[spring-webmvc-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:938) [spring-webmvc-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:877) [spring-webmvc-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:966) [spring-webmvc-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:868) [spring-webmvc-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:646) [servlet-api.jar:?] 
    at org.springframework.web.servlet.FrameworkServlet.service(FrameworkServlet.java:842) [spring-webmvc-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at javax.servlet.http.HttpServlet.service(HttpServlet.java:727) [servlet-api.jar:?] 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:303) [catalina.jar:7.0.57] 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208) [catalina.jar:7.0.57] 
    at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52) [tomcat7-websocket.jar:7.0.57] 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241) [catalina.jar:7.0.57] 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208) [catalina.jar:7.0.57] 
    at mordeth.orchestration.controller.CorsFilter.doFilterInternal(CorsFilter.java:21) [CorsFilter.class:?] 
    at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:107) [spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241) [catalina.jar:7.0.57] 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208) [catalina.jar:7.0.57] 
    at org.apache.shiro.web.servlet.AbstractShiroFilter.executeChain(AbstractShiroFilter.java:449) [shiro-web-1.2.0.jar:1.2.0] 
    at org.apache.shiro.web.servlet.AbstractShiroFilter$1.call(AbstractShiroFilter.java:365) [shiro-web-1.2.0.jar:1.2.0] 
    at org.apache.shiro.subject.support.SubjectCallable.doCall(SubjectCallable.java:90) [shiro-core-1.2.0.jar:1.2.0] 
    at org.apache.shiro.subject.support.SubjectCallable.call(SubjectCallable.java:83) [shiro-core-1.2.0.jar:1.2.0] 
    at org.apache.shiro.subject.support.DelegatingSubject.execute(DelegatingSubject.java:380) [shiro-core-1.2.0.jar:1.2.0] 
    at org.apache.shiro.web.servlet.AbstractShiroFilter.doFilterInternal(AbstractShiroFilter.java:362) [shiro-web-1.2.0.jar:1.2.0] 
    at org.apache.shiro.web.servlet.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:125) [shiro-web-1.2.0.jar:1.2.0] 
    at org.springframework.web.filter.DelegatingFilterProxy.invokeDelegate(DelegatingFilterProxy.java:344) [spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.springframework.web.filter.DelegatingFilterProxy.doFilter(DelegatingFilterProxy.java:261) [spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241) [catalina.jar:7.0.57] 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208) [catalina.jar:7.0.57] 
    at org.apache.logging.log4j.web.Log4jServletFilter.doFilter(Log4jServletFilter.java:67) [log4j-web-2.0.jar:2.0] 
    at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:241) [catalina.jar:7.0.57] 
    at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:208) [catalina.jar:7.0.57] 
    at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:220) [catalina.jar:7.0.57] 
    at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:122) [catalina.jar:7.0.57] 
    at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:503) [catalina.jar:7.0.57] 
    at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:170) [catalina.jar:7.0.57] 
    at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:103) [catalina.jar:7.0.57] 
    at org.apache.catalina.valves.AccessLogValve.invoke(AccessLogValve.java:950) [catalina.jar:7.0.57] 
    at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:116) [catalina.jar:7.0.57] 
    at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:421) [catalina.jar:7.0.57] 
    at org.apache.coyote.http11.AbstractHttp11Processor.process(AbstractHttp11Processor.java:1070) [tomcat-coyote.jar:7.0.57] 
    at org.apache.coyote.AbstractProtocol$AbstractConnectionHandler.process(AbstractProtocol.java:611) [tomcat-coyote.jar:7.0.57] 
    at org.apache.tomcat.util.net.JIoEndpoint$SocketProcessor.run(JIoEndpoint.java:314) [tomcat-coyote.jar:7.0.57] 
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145) [?:1.7.0_71] 
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615) [?:1.7.0_71] 
    at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61) [tomcat-coyote.jar:7.0.57] 
    at java.lang.Thread.run(Thread.java:745) [?:1.7.0_71] 
Caused by: com.fasterxml.jackson.databind.JsonMappingException: getInputStream() has already been called for this request (through reference chain: org.apache.shiro.web.servlet.ShiroHttpServletRequest["request"]->org.apache.catalina.connector.RequestFacade["reader"]) 
    at com.fasterxml.jackson.databind.JsonMappingException.wrapWithPath(JsonMappingException.java:210) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.JsonMappingException.wrapWithPath(JsonMappingException.java:177) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.std.StdSerializer.wrapAndThrow(StdSerializer.java:190) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:671) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:156) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:575) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:663) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:156) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.DefaultSerializerProvider.serializeValue(DefaultSerializerProvider.java:129) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ObjectMapper.writeValue(ObjectMapper.java:2238) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.writeInternal(AbstractJackson2HttpMessageConverter.java:231) ~[spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    ... 52 more 
Caused by: java.lang.IllegalStateException: getInputStream() has already been called for this request 
    at org.apache.catalina.connector.Request.getReader(Request.java:1239) ~[catalina.jar:7.0.57] 
    at org.apache.catalina.connector.RequestFacade.getReader(RequestFacade.java:505) ~[catalina.jar:7.0.57] 
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[?:1.7.0_71] 
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57) ~[?:1.7.0_71] 
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) ~[?:1.7.0_71] 
    at java.lang.reflect.Method.invoke(Method.java:606) ~[?:1.7.0_71] 
    at com.fasterxml.jackson.databind.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:536) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:663) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:156) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.BeanPropertyWriter.serializeAsField(BeanPropertyWriter.java:575) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.std.BeanSerializerBase.serializeFields(BeanSerializerBase.java:663) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.BeanSerializer.serialize(BeanSerializer.java:156) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ser.DefaultSerializerProvider.serializeValue(DefaultSerializerProvider.java:129) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at com.fasterxml.jackson.databind.ObjectMapper.writeValue(ObjectMapper.java:2238) ~[jackson-databind-2.5.0.jar:2.5.0] 
    at org.springframework.http.converter.json.AbstractJackson2HttpMessageConverter.writeInternal(AbstractJackson2HttpMessageConverter.java:231) ~[spring-web-4.1.4.RELEASE.jar:4.1.4.RELEASE] 
    ... 52 more 
+0

Phiên bản mùa xuân của bạn là gì? –

+0

Xin chào, phiên bản mùa xuân của tôi là 4.1.4.RELEASE và jackson impl là phiên bản fastxml 2.5.0 –

Trả lời

20

Sử dụng chuỗi thay vì AuthenticationResponse. Nếu bạn nhận được phản hồi trống, giá trị Chuỗi sẽ trống.

ResponseEntity<String> authenticateResponse = restTemplate.getForEntity(authenticateUrl, String.class); 

Cập nhật: Kiểm tra điều này link. Tôi nghĩ điều này sẽ khắc phục được sự cố của bạn.

ResponseEntity<Void> response = restTemplate.getForEntity(authenticateUrl,Void.class); 
Void body = response.getBody(); 
+0

Cảm ơn, Hareesh. Tôi đã hy vọng restTemplate sẽ có một cách thanh lịch để xử lý 204 Không có nội dung hoặc cho rằng bất kỳ mã http khác mà dịch vụ nghỉ ngơi có thể giao tiếp với khách hàng của họ chỉ thông qua mã http và không phải có bất kỳ trọng tải –

+1

btw, điều này không thành công, tôi ' d cần phải có các dịch vụ còn lại có một loại trả về (String) thay vì void –

+0

String làm việc cho tôi là tốt – chrismarx

Các vấn đề liên quan