2017-01-12 36 views
1

我有一个要求,使用Spring MVC重定向到一个外部服务,使用POST来构建一个对象。Spring MVC重定向与来自HTTP POST的响应

从阅读this previous question据我所知,通过Spring MVC重定向是不可能的,所以需要通过Java代码中的HTTP客户端完成POST请求,我可以通过一个例子一个发现here

我需要能够将浏览器重定向到POST请求的响应,但我不知道如何使用Spring MVC。

控制器

@RequestMapping(method = RequestMethod.GET, value = "/handoff") 
public HttpEntity dispatch(HttpServletRequest request, 
    @RequestParam(value = "referralURL", required = false) String referralUrl) { 

    String redirectURL = "http://desinationURL.com/post"; 

    HttpClientHelper httpHelper = new HttpClientHelper(); 
    HttpEntity entity = httpHelper.httpClientPost(redirectURL, null); 

    // Redirect 
    return entity; 
} 

HttpClientHelper.java

public HttpEntity httpClientPost(String url, List<NameValuePair> params) throws ClientProtocolException, IOException { 

    HttpClient httpclient = HttpClients.createDefault(); 
    HttpPost httppost = new HttpPost(url); 

    // Request parameters and other properties. 
    if (params != null) { 
     httppost.setEntity(new UrlEncodedFormEntity(params, Constants.UTF_8_ENCODING)); 
    } 

    // Execute and get the response. 
    HttpResponse response = httpclient.execute(httppost); 
    HttpEntity entity = response.getEntity(); 

    return entity; 

} 

我可以看到,目标服务是由POST请求命中成功,我需要读取响应作为返回的输出因为它现在刚刚返回一个404.

回答

0

使用sendRedirect代替HttpClient,您的控制器方法应该如下所示。

@RequestMapping(method = RequestMethod.GET, value = "/handoff") 
public HttpEntity dispatch(HttpServletRequest request, HttpServletResponse response, 
    @RequestParam(value = "referralURL", required = false) String referralUrl) { 

    String redirectURL = "http://desinationURL.com/post"; 

    response.setStatus(HttpServletResponse.SC_TEMPORARY_REDIRECT); 
    response.setHeader("Location", redirectURL); 

    // Redirect 
    return entity; 
} 
+0

我已经包括HttpServletResponse的并置和首部值的建议,但它不重定向,还是返回404我是否需要改变方法返回响应而不是HttpEntity? –

1

不能重定向浏览器POST请求的响应。您只需将呼叫结果发送回外部URL即可。或者以某种方式处理响应,然后转发到应用程序中的某个其他页面,该页面显示有关响应的一些信息。

例如

@RequestMapping(method = RequestMethod.GET, value = "/handoff") 
public void dispatch(HttpServletRequest request, 
    @RequestParam(value = "referralURL", required = false) String referralUrl, HttpServletResponse response) { 

    String redirectURL = "http://desinationURL.com/post"; 

    HttpClientHelper httpHelper = new HttpClientHelper(); 
    HttpEntity entity = httpHelper.httpClientPost(redirectURL, null); 

    //streams the raw response 
    entity.writeTo(response.getOutputSStream()); 
} 
0

如果你有兴趣在一个更复杂的解决方案,您可以利用Zuul为,并有zuul管理请求转发。 https://github.com/Netflix/zuul在过滤器链中,您可以根据需要操作请求。

1

这是我做的

CloseableHttpClient httpClient = HttpClients.custom() 
      .setRedirectStrategy(new LaxRedirectStrategy()) 
      .build(); 

    //this reads the input stream from POST 
    ServletInputStream str = request.getInputStream(); 

    HttpPost httpPost = new HttpPost(path); 
    HttpEntity postParams = new InputStreamEntity(str); 
    httpPost.setEntity(postParams); 

    HttpResponse httpResponse = null ; 
    int responseCode = -1 ; 
    StringBuffer response = new StringBuffer(); 

    try { 

     httpResponse = httpClient.execute(httpPost); 

     responseCode = httpResponse.getStatusLine().getStatusCode(); 
     logger.info("POST Response Status:: {} for file {} ", responseCode, request.getQueryString()); 

     //return httpResponse ; 
     BufferedReader reader = new BufferedReader(new InputStreamReader(
       httpResponse.getEntity().getContent())); 

     String inputLine; 
     while ((inputLine = reader.readLine()) != null) { 
      response.append(inputLine); 
     } 
     reader.close(); 

     logger.info(" Final Complete Response {} " + response.toString()); 
     httpClient.close(); 

    } catch (Exception e) { 

     logger.error("Exception ", e); 

    } finally { 

     IOUtils.closeQuietly(httpClient); 

    } 

    // Return the response back to caller 
    return new ResponseEntity<String>(response.toString(), HttpStatus.ACCEPTED);