java Spring 4 @RequestMapping -- 消耗 vs 标头?

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/30923249/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-02 17:50:21  来源:igfitidea点击:

Spring 4 @RequestMapping -- consumes vs headers?

javaspringrestspring-mvc

提问by Chris

I'm learning how to build RESTful web services using Spring 4, and one thing I'm not clear on is in @RequestMapping. I've seen examples where one uses headers = "Accept=application/xml"and other examples using consumes (or produces) = "application/xml".

我正在学习如何使用 Spring 4 构建 RESTful Web 服务,我不清楚的一件事是在 @RequestMapping 中。我已经看到了一个使用headers = "Accept=application/xml"和其他使用消耗(或生产)的例子= "application/xml"

For instance, in my own @RestController class, I have this function...

例如,在我自己的@RestController 类中,我有这个功能......

// POST
@RequestMapping(method = RequestMethod.POST, headers = "Accept=application/xml")
public User create(@RequestBody User user) {
    LOG.info("User = " + user.toString());
return userService.create(user);
}

What is the difference between using headers = "Accept=application/xml"vs. using consumes = "application/xml"?Or even using headers = "content-type=application/xml"?

usingheaders = "Accept=application/xml"与 using 消耗= "application/xml"?或什至使用有headers = "content-type=application/xml"什么区别?

Could someone explain the differences between headers and consumes/produces, and when each is used?

有人可以解释标题和消费/生产之间的区别,以及何时使用它们吗?

回答by Alex Ander

SHORT ANSWER
In the example you have above, using headers = "Accept=application/xml"or produces = "application/xml"will both respond to the client the same way i.e. send a response to the client with XML representation.

简短回答
在上面的示例中,使用headers = "Accept=application/xml"produces = "application/xml"都将以相同的方式响应客户端,即使用 XML 表示向客户端发送响应。

LONGER ANSWER
i. Headers
For RESTful web services, the client (e.g. your browser) sends a request (e.g. GET, POST, etc.) to a server, and the server will send a response back. This is an HTTP Transaction. Both the request and response have HTTP header fields ("headers"), which define the operating parameters of an HTTP transaction (I will refer to the headers for client request as "request headers", and these differ from headers from server response "response headers").

更长的答案
i. 标头
对于 RESTful Web 服务,客户端(例如您的浏览器)向服务器发送请求(例如 GET、POST 等),服务器将返回响应。这是一个 HTTP 事务。请求和响应都有 HTTP 头域(“headers”),它定义了一个 HTTP 事务的操作参数(我将客户端请求的头称为“请求头”,它们不同于服务器响应的头“响应”标题”)。

As part of the request your browser sends to server, there are different request headers and some examples include Accept, Connection, Content-Lengthetc. and each of these headers have their own function (see a full list of headers here: https://en.wikipedia.org/wiki/List_of_HTTP_header_fields).

由于您的浏览器向服务器发送请求的一部分,也有不同的请求头和一些例子包括AcceptConnectionContent-Length等,并且每个头都有自己的功能(在这里看到头的完整列表:HTTPS://en.wikipedia。 org/wiki/List_of_HTTP_header_fields)。

Using your code example, if a client does a POST request, Spring will check the request header(s) and if it finds a header Acceptwith a value of application/xml, it will map the request to the createmethod you have above (and in your case the server will return an XML response representation to the client).

使用您的代码示例,如果客户端发出 POST 请求,Spring 将检查请求标头,如果找到Accept值为 的标头application/xml,它会将请求映射到create您上面的方法(在您的情况下服务器将向客户端返回一个 XML 响应表示)。

Let me modify the headerselement in the code you provided:

让我修改headers您提供的代码中的元素:

@RequestMapping(method = RequestMethod.POST, headers = "Connection=keep-alive")
public User create(@RequestBody User user) {
 ...
}

Notice the headerselement now has a value of Connection=keep-alive. If a client does a POST request, Spring will check the request header(s) and if it finds a header Connectionwith a value of keep-alive, it will map that client request to the createmethod above.

请注意,该headers元素现在的值为Connection=keep-alive。如果客户端发出 POST 请求,Spring 将检查请求标头,如果找到Connection值为 的标头keep-alive,它将将该客户端请求映射到上述create方法。

ii. Produces and Consumes
If you used produces="application/xml"for the createmethod, this means a client request is only mapped to the createmethod if the client's Acceptheader matches application/xml. This essentially is the client saying, "Hey server, I prefer to accept your response in XML representation, so send your response to me in XML". Effectively, the produces="application/xml"is also the server saying, "Hey client, I can only produce responses for you in XML representation, so I will send you that format". Link to Spring documentation reference.

ii. Produces 和 Consumes
如果您使用produces="application/xml"了该create方法,这意味着只有create在客户端的Accept标头匹配时,客户端请求才会映射到该方法application/xml。这本质上是客户端说,“嘿,服务器,我更喜欢以 XML 表示形式接受您的响应,所以将您的响应以 XML 格式发送给我”。实际上,这produces="application/xml"也是服务器说,“嘿,客户端,我只能以 XML 表示为您生成响应,因此我将向您发送该格式”。 链接到 Spring 文档参考

If you used consumes="application/xml"for the createmethod, this means a client request is only mapped to the createmethod if the client's Content-Typeheader matches application/xml(the Content-Typerequest header describes the representation the client request is coming in). This essentially is the server saying, "Hey client, I can only consume requests in XML representation, so send that format to me".

如果使用consumes="application/xml"create方法,这意味着客户机请求仅映射到create如果客户端的方法Content-Type报头匹配application/xml(在Content-Type请求报头描述了客户端请求在即将到来的表示)。这本质上是服务器说,“嘿,客户端,我只能使用 XML 表示形式的请求,所以请将该格式发送给我”。

SUMMARY
The headerselement within the @RequestMappingannotation can take different request headers (Accept, Connection, Cache-Controletc.), but the produceselement is only concerned with the Acceptrequest header and the consumeselement is only concerned with the Content-Typerequest header.

发明内容
所述headers的范围内元件@RequestMapping注释可以采取不同的请求头(AcceptConnectionCache-Control等),但该produces元件仅关心Accept请求报头和所述consumes元件仅关心的Content-Type请求报头。

回答by Sotirios Delimanolis

As the javadoc of HeadersRequestCondition(which handles the value provided in the headersattribute of a @RequestMappingannotation) states

正如HeadersRequestCondition(处理注释的headers属性中提供的值)的 javadoc所述@RequestMapping

Expressions passed to the constructor with header names 'Accept' or 'Content-Type' are ignored. See ConsumesRequestConditionand ProducesRequestConditionfor those.

传递给构造函数的带有标题名称“Accept”或“Content-Type”的表达式将被忽略。看到ConsumesRequestConditionProducesRequestCondition那些。

So don't use those headers in headers. Use the producesand consumesattributes for Acceptand Content-Type.

所以不要在headers. 使用producesconsumes属性的AcceptContent-Type

As to how to use them, the documentation gives examples: for consumesand for produces.

至于如何使用它们,文档给出了示例:forconsumesforproduces