简体   繁体   English

Spring MVC重定向,HTTP POST响应

[英]Spring MVC Redirect with Response from HTTP POST

I have a requirement to use Spring MVC to redirect to an external service using a POST with an object that is built. 我要求使用带有已建对象的POST使用Spring MVC重定向到外部服务。

From reading this previous question I understand that it is not possible to do so via Spring MVC redirect, so it is required to complete the POST request via a HTTP client in the Java code, which I can do via an example such as the one found here . 通过阅读上一个问题,我知道无法通过Spring MVC重定向来完成此操作,因此需要通过Java代码中的HTTP客户端来完成POST请求,我可以通过一个示例(例如找到的示例)来完成在这里

I need to be able to redirect the browser to the response of the POST request, but I am not sure how to do so using Spring MVC. 我需要能够将浏览器重定向到POST请求的响应,但是我不确定如何使用Spring MVC做到这一点。

Controller 调节器

@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 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;

}

I can see that the target service is being hit by the POST request successfully, I need to read the output of the response as a return value from the MCV controller as it currently just returns a 404. 我可以看到POST请求已成功击中目标服务,我需要从MCV控制器读取响应的输出作为返回值,因为它当前仅返回404。

You cannot redirect the browser to the response of the POST request. 您不能浏览器重定向到POST请求的响应。 All you can do is send back the result of the call to the external URL. 您所要做的就是将调用结果发送回外部URL。 Or process the response in some way and then forward to some other page in your application which displays some information about the response. 或者以某种方式处理响应,然后转发到应用程序中的其他页面,该页面显示有关响应的一些信息。

eg 例如

@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());
}

This is how I did it 这就是我做的

    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);

Use sendRedirect instead of HttpClient, your controller method should look like below. 使用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;
}

If you're interested in a more involved solution you can leverage Zuul for that and have zuul manage the request forwarding. 如果您对更复杂的解决方案感兴趣,则可以利用Zuul并让zuul管理请求转发。 https://github.com/Netflix/zuul During the filter chain you can manipulate the request however you want. https://github.com/Netflix/zuul在过滤器链中,您可以根据需要操纵请求。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM