是否有必要包装在支持对象中?我想这样做:
@RequestMapping(value = "/Test", method = RequestMethod.POST)
@ResponseBody
public boolean getTest(@RequestBody String str1, @RequestBody String str2) {}
并像这样使用JSON:
{
"str1": "test one",
"str2": "two test"
}
但我不得不使用:
@RequestMapping(value = "/Test", method = RequestMethod.POST)
@ResponseBody
public boolean getTest(@RequestBody Holder holder) {}
然后使用这个JSON:
{
"holder": {
"str1": "test one",
"str2": "two test"
}
}
对吗?我的另一个选择是将RequestMethod
更改为GET
并在查询字符串中使用@RequestParam
,或者将@PathVariable
与RequestMethod
一起使用。
发布于 2012-10-15 22:19:33
您是对的,带注释的@RequestBody参数应该包含请求的整个正文并绑定到一个对象,因此您基本上必须使用您的选项。
如果你绝对想要你的方法,有一个自定义的实现,你可以这样做:
假设这是你的json:
{
"str1": "test one",
"str2": "two test"
}
你想把它绑定到这里的两个参数上:
@RequestMapping(value = "/Test", method = RequestMethod.POST)
public boolean getTest(String str1, String str2)
首先定义一个自定义注释,比如@JsonArg
,其中包含指向所需信息的JSON path:
public boolean getTest(@JsonArg("/str1") String str1, @JsonArg("/str2") String str2)
现在编写一个自定义HandlerMethodArgumentResolver,它使用上面定义的JsonPath来解析实际的参数:
import java.io.IOException;
import javax.servlet.http.HttpServletRequest;
import org.apache.commons.io.IOUtils;
import org.springframework.core.MethodParameter;
import org.springframework.http.server.ServletServerHttpRequest;
import org.springframework.web.bind.support.WebDataBinderFactory;
import org.springframework.web.context.request.NativeWebRequest;
import org.springframework.web.method.support.HandlerMethodArgumentResolver;
import org.springframework.web.method.support.ModelAndViewContainer;
import com.jayway.jsonpath.JsonPath;
public class JsonPathArgumentResolver implements HandlerMethodArgumentResolver{
private static final String JSONBODYATTRIBUTE = "JSON_REQUEST_BODY";
@Override
public boolean supportsParameter(MethodParameter parameter) {
return parameter.hasParameterAnnotation(JsonArg.class);
}
@Override
public Object resolveArgument(MethodParameter parameter, ModelAndViewContainer mavContainer, NativeWebRequest webRequest, WebDataBinderFactory binderFactory) throws Exception {
String body = getRequestBody(webRequest);
String val = JsonPath.read(body, parameter.getMethodAnnotation(JsonArg.class).value());
return val;
}
private String getRequestBody(NativeWebRequest webRequest){
HttpServletRequest servletRequest = webRequest.getNativeRequest(HttpServletRequest.class);
String jsonBody = (String) servletRequest.getAttribute(JSONBODYATTRIBUTE);
if (jsonBody==null){
try {
String body = IOUtils.toString(servletRequest.getInputStream());
servletRequest.setAttribute(JSONBODYATTRIBUTE, body);
return body;
} catch (IOException e) {
throw new RuntimeException(e);
}
}
return "";
}
}
现在只需将其注册到Spring MVC。有点牵涉其中,但这应该能干净利落地工作。
发布于 2015-11-17 13:17:39
虽然@RequestBody
必须映射到单个对象是事实,但该对象可以是一个Map
,因此这为您提供了一个实现目标的好方法(不需要编写一个一次性的后备对象):
@RequestMapping(value = "/Test", method = RequestMethod.POST)
@ResponseBody
public boolean getTest(@RequestBody Map<String, String> json) {
//json.get("str1") == "test one"
}
如果你想要一个完整的ObjectNode树,你也可以绑定到杰克逊的JSON:
public boolean getTest(@RequestBody ObjectNode json) {
//json.get("str1").asText() == "test one"
发布于 2019-03-10 13:59:07
用于传递多个对象、参数、变量等。您可以使用jackson库中的ObjectNode作为您的参数来动态完成此操作。你可以这样做:
@RequestMapping(value = "/Test", method = RequestMethod.POST)
@ResponseBody
public boolean getTest(@RequestBody ObjectNode objectNode) {
// And then you can call parameters from objectNode
String strOne = objectNode.get("str1").asText();
String strTwo = objectNode.get("str2").asText();
// When you using ObjectNode, you can pas other data such as:
// instance object, array list, nested object, etc.
}
我希望这能有所帮助。
https://stackoverflow.com/questions/12893566
复制相似问题