【问题标题】:How to send XML POST requests with Spring RestTemplate?如何使用 Spring RestTemplate 发送 XML POST 请求?
【发布时间】:2016-05-29 10:04:23
【问题描述】:

是否可以使用spring 发送XML POST 请求,例如RestTemplate

我想将下面的xml发送到urllocalhost:8080/xml/availability

<AvailReq>
  <hotelid>123</hotelid>
</AvailReq>

我还想在每个请求上动态添加自定义 http 标头(!)。

我如何使用 spring 实现这一点?

【问题讨论】:

    标签: java xml spring


    【解决方案1】:

    首先,定义HTTP 标头,如下所示:

    HttpHeaders headers = new HttpHeaders();
    headers.add("header_name", "header_value");
    

    您可以使用这种方法设置任何HTTP 标头。对于众所周知的标题,您可以使用预定义的方法。比如为了设置Content-Type header:

    headers.setContentType(MediaType.APPLICATION_XML);
    

    然后定义一个HttpEntityRequestEntity 来准备你的请求对象:

    HttpEntity<String> request = new HttpEntity<String>(body, headers);
    

    如果您以某种方式可以访问XML 字符串,则可以使用HttpEntity&lt;String&gt;。否则,您可以定义与该XML 对应的 POJO。最后使用postFor... 方法发送请求:

    ResponseEntity<String> response = restTemplate.postForEntity("http://localhost:8080/xml/availability", request, String.class);
    

    这里我将POST 请求发送到http://localhost:8080/xml/availability 端点并将HTTP 响应正文转换为String

    注意,在上面的例子中new HttpEntity&lt;String&gt;(...)可以be replaced withnew HttpEntity&lt;&gt;(...)使用JDK7及更高版本。

    【讨论】:

    • 好的,我明白了,谢谢。我从XSDs 自动生成了JAXB 类。如果传出必须是application/xml 并且响应是text/html,那么我怎么能让RestTemplate 转换这些,但一切都只是xml。
    • 使用你的JAXB 类,比如SomeClass,而不是String。实际上是HttpEntity&lt;SomeClass&gt; request = ...
    • Jaxb2RootElementHttpMessageConverter 会将您的 JAXB 类转换为 XML。它应该默认注册。如果由于某种原因未注册,请手动注册。
    • 对于HTML 响应,如果需要,您可以将Accept 标头设置为text/html。但是您仍然可以在 postFor... 方法中使用 String 作为预期的正文类型。
    【解决方案2】:

    下面是一个完整的示例,如何使用RestTemplate 交换 XML 文档并接收 HTML 响应:

    import static org.hamcrest.Matchers.is;
    import static org.junit.Assert.assertThat;
    import static org.springframework.test.web.client.match.MockRestRequestMatchers.header;
    import static org.springframework.test.web.client.match.MockRestRequestMatchers.content;
    import static org.springframework.test.web.client.match.MockRestRequestMatchers.method;
    import static org.springframework.test.web.client.match.MockRestRequestMatchers.requestTo;
    import static org.springframework.test.web.client.response.MockRestResponseCreators.withSuccess;
    
    import org.junit.Test;
    import org.springframework.http.HttpEntity;
    import org.springframework.http.HttpHeaders;
    import org.springframework.http.HttpMethod;
    import org.springframework.http.MediaType;
    import org.springframework.http.ResponseEntity;
    import org.springframework.test.web.client.MockRestServiceServer;
    import org.springframework.web.client.RestTemplate;
    import org.w3c.dom.Document;
    import org.xml.sax.InputSource;
    
    import java.io.StringReader;
    
    import javax.xml.parsers.DocumentBuilder;
    import javax.xml.parsers.DocumentBuilderFactory;
    
    public class XmlTest {
    
        @Test
        public void test() throws Exception {
            RestTemplate restTemplate = new RestTemplate();
            MockRestServiceServer mockServer = MockRestServiceServer.createServer(restTemplate);
            String htmlString = "<p>response</p>";
            String xmlString = "<?xml version=\"1.0\" encoding=\"utf-8\"?><AvailReq><hotelid>123</hotelid></AvailReq>";
    
            DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
            DocumentBuilder builder = factory.newDocumentBuilder();
            Document document = builder.parse(new InputSource(new StringReader(xmlString)));
    
            mockServer.expect(requestTo("http://localhost:8080/xml/availability"))
                    .andExpect(method(HttpMethod.POST))
                    .andExpect(content().string(is(xmlString)))
                    .andExpect(header("header", "value"))
                    .andRespond(withSuccess("<p>response</p>", MediaType.TEXT_HTML));
    
            HttpHeaders headers = new HttpHeaders();
            headers.add("header", "value");
            HttpEntity<Document> request = new HttpEntity<>(document, headers);
    
            final ResponseEntity<String> response = restTemplate.postForEntity("http://localhost:8080/xml/availability", request, String.class);
    
            assertThat(response.getBody(), is(htmlString));
            mockServer.verify();
        }
    }
    

    【讨论】:

      【解决方案3】:

      查找以下示例以使用 RestTemplate 将 XML 交换为字符串并接收响应:

      String xmlString = "<?xml version=\"1.0\" encoding=\"utf-8\"?><AvailReq><hotelid>123</hotelid></AvailReq>";
      
          RestTemplate restTemplate =  new RestTemplate();
          //Create a list for the message converters
          List<HttpMessageConverter<?>> messageConverters = new ArrayList<HttpMessageConverter<?>>();
          //Add the String Message converter
          messageConverters.add(new StringHttpMessageConverter());
          //Add the message converters to the restTemplate
          restTemplate.setMessageConverters(messageConverters);
      
      
          HttpHeaders headers = new HttpHeaders();
          headers.setContentType(MediaType.APPLICATION_XML);
          HttpEntity<String> request = new HttpEntity<String>(xmlString, headers);
      
          final ResponseEntity<String> response = restTemplate.postForEntity("http://localhost:8080/xml/availability", request, String.class);
      

      【讨论】:

      • 通过 url 反序列化 Soap xml 的有用答案
      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2017-04-16
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多