Spring MVC Spring请求Map不拆分请求参数和请求正文

siv3szwd  于 2023-01-21  发布在  Spring
关注(0)|答案(1)|浏览(170)
    • bounty将在6天后过期**。回答此问题可获得+50声望奖励。Sampisa希望引起更多人关注此问题。

我想实现一个POST端点,在这里可以通过编程接受或拒绝发送的数据,这取决于它是来自querystring还是来自x-www-form-urlencoded数据。

@PostMapping(value="/api/signin")
ResponseEntity<SigninResponse> signin(
     @RequestParam(value = "username", required = false) String username,
     @RequestParam(value = "password", required = false) String password,
     @RequestBody(required = false) @ModelAttribute SigninRequest sr) {
        // here if I POST a SigninRequest without queryString, aka
        // user/pass sent in x-www-form-urlencoded, both sr and 
        // username+password vars are filled. The same, if I send 
        // username+password on querystring, without any data 
        // on x-www-form-urlencoded, also sr is filled
     }

如果我删除"@ModelAttribute ",那么带有querystring的POST就可以工作,但是带有x-www-form-urlencoded的POST会引发一个异常" Content type "application/x-www-form-urlencoded;charset = UTF-8 "不支持"(为什么?)并返回415(不支持的媒体类型)。
无论如何,我正在寻找一种方法来理解何时POST数据来自querystring,何时数据来自x-www-form-urlencoded,以编程方式启用/禁用一种方法与另一种方法。我最终可以编写两种不同的方法(都在POST中),而不需要只使用一种方法。
有什么建议吗?
谢谢你。

92dk7w1h

92dk7w1h1#

这个问题的一个解决方案是在应该绑定到请求参数的方法参数上使用@RequestParam注解,在应该绑定到请求主体的方法参数上使用@RequestBody注解,这样,Spring就知道请求的每个部分应该使用哪个参数。
例如,如果您有这样的方法:

@RequestMapping(value = "/api/signin", method = RequestMethod.POST)
public void signin(@RequestParam String requestParam, @RequestBody ExampleRequest requestBody) {
    // do something with requestParam and requestBody
}

Spring将知道将requestParam请求参数绑定到requestParam方法参数,并将请求主体绑定到requestBody方法参数。
另一种解决方案是将请求参数和请求主体定义为单独的方法,例如:

@RequestMapping(value = "/api/signin", method = RequestMethod.POST)
public void signin(@RequestBody ExampleRequest requestBody) {
    // do something with requestBody
}

@RequestMapping(value = "/api/signin", method = RequestMethod.GET)
public void signin(@RequestParam String requestParam) {
    // do something with requestParam
}

您还应该确保请求头设置正确,例如在发送JSON请求正文时将Content-Type头设置为application/json
作为另一种解决方案,您可以使用@RequestPart注解代替@RequestParam@RequestPart注解允许您指定请求主体的哪一部分应该用于特定的参数。这样,您可以分离RequestParamRequestBody参数,并让Spring分别处理它们。此外,您还可以使用@ModelAttribute注解将多个请求参数绑定到单个对象中。

相关问题