> For the complete documentation index, see [llms.txt](https://potoyang.gitbook.io/spring-in-action-v4/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://potoyang.gitbook.io/spring-in-action-v4/di-16-zhang-shi-yong-spring-mvc-chuang-jian-rest-api/untitled-1/untitled-2.md).

# 16.4.8　在 POST 请求中获取响应对象

假设你正在使用 RestTemplate 来 POST 一个新的 Spitter 对象到 Spittr 应用程序的 REST API。因为这是一个全新的 Spitter，服务端并（还）不知道它。因此，它还不是真正的 REST 资源，也没有 URL。另外，在服务端创建之前，客户端并不知道 Spitter 的 ID。

POST资源到服务端的一种方式是使用 RestTemplate 的 postForObject() 方法。postForObject() 方法的三个变种签名如下：

```java
<T> T postForObject(String url, Object request, Class<T> responseType, Object... uriVariables)
			throws RestClientException;

<T> T postForObject(String url, Object request, Class<T> responseType, Map<String, ?> uriVariables)
			throws RestClientException;

<T> T postForObject(URI url, Object request, Class<T> responseType) throws RestClientException;
```

在所有情况下，第一个参数都是资源要 POST 到的 URL，第二个参数是要发送的对象，而第三个参数是预期返回的 Java 类型。在将 URL 作为 String 类型的两个版本中，第四个参数指定了 URL 变量（要么是可变参数列表，要么是一个 Map）。

当 POST 新的 Spitter 资源到 Spitter REST API 时，它们应该发送到 <http://localhost:8080/spittr-api/spitters>，这里会有一个应对 POST 请求的处理方法来保存对象。因为这个 URL 不需要 URL 参数，所以我们可以使用任何版本的 postForObject()。但为了保持尽可能简单，我们可以这样调用：

```java
public Spitter postSpitterForObject(Spitter spitter) {
  RestTemplate rest = new RestTemplate();
  return rest.postForObject("http://localhost:8080/spittr-api/spitters",
    spitter, Spitter.class);
}
```

postSpitterForObject() 方法给定了一个新创建的 Spitter 对象，并使用 postForObject() 将其发送到服务器端。在响应中，它接收到一个 Spitter 对象并将其返回给调用者。

就像 getForEntity() 方法一样，你可能想得到请求带回来的一些元数据。在这种情况下，postForEntity() 是更合适的方法。postForEntity() 方法有着与 postForObject() 几乎相同的一组签名：

```java
<T> ResponseEntity<T> postForEntity(String url, Object request, Class<T> responseType, Object... uriVariables)
			throws RestClientException;

<T> ResponseEntity<T> postForEntity(String url, Object request, Class<T> responseType, Map<String, ?> uriVariables)
			throws RestClientException;

<T> ResponseEntity<T> postForEntity(URI url, Object request, Class<T> responseType) throws RestClientException;
```

假设除了要获取返回的 Spitter 资源，还要查看响应中 Location 头信息的值。在这种情况下，你可以这样调用 postForEntity()：

```java
RestTemplate rest = new RestTemplate();
ResponseEntity<Spitter> response = rest.postForEntity(
  "http://localhost:8080/spittr-api/spitters",
  spitter, Spitter.class);
Spitter spitter = response.getBody();
URI url = response.getHeaders().getLocation();
```

与 getForEntity() 方法一样，postForEntity() 返回一个 ResponseEntity 对象。你可以调用这个对象的 getBody() 方法以获取资源对象（在本示例中是 Spitter）。getHeaders() 会给你一个 HttpHeaders，通过它可以访问响应中返回的各种 HTTP头信息。这里，我们调用 getLocation() 来得到 java.net.URI 形式的 Location 头信息。
