Reputation: 7391
I have this controller method:
@PostMapping(
value = "/createleave",
params = {"start","end","hours","username"})
public void createLeave(@RequestParam(value = "start") String start,
@RequestParam(value = "end") String end,
@RequestParam(value = "hours") String hours,
@RequestParam(value = "username") String username){
System.out.println("Entering createLeave " + start + " " + end + " " + hours + " " + username);
LeaveQuery newLeaveQuery = new LeaveQuery();
Account account = accountRepository.findByUsername(username);
newLeaveQuery.setAccount(account);
newLeaveQuery.setStartDate(new Date(Long.parseLong(start)));
newLeaveQuery.setEndDate(new Date(Long.parseLong(end)));
newLeaveQuery.setTotalHours(Integer.parseInt(hours));
leaveQueryRepository.save(newLeaveQuery);
}
However when I send a post request to this endpoint I get the following
"{"timestamp":1511444885321,"status":400,"error":"Bad Request","exception":"org.springframework.web.bind.UnsatisfiedServletRequestParameterException","message":"Parameter conditions \"start, end, hours, username\" not met for actual request parameters: ","path":"/api/createleave"}"
When I remove the params argument from the @PostMapping
annotation I get a more general error, it will say that it cannot find the first required parameter (start), while it really is being send together with the parameters end, hours and username.
how to get param in method post spring mvc?
I've read in this post that @RequestParam
can only be used for get methods, but if I remove @RequestParam
and stick with the params argument of the @PostMapping
annotation it still doesn't work. I know I can use @RequestBody
but I do not want to make a class just for those 4 parameters. Can anyone tell me how I can make this work?
Thank you
EDIT: I'm reading here https://docs.spring.io/spring/docs/current/javadoc-api/org/springframework/web/bind/annotation/RequestMapping.html#params-- that the argument params isn't exactly what I thought it was. It seems to be used as a condition. If a set of parameters match a value then the endpoint controller method will be activated.
Upvotes: 40
Views: 118738
Reputation: 11130
Well, the answer by @Sync is fundamentally wrong and not the question being asked.
@RequestParam
in a lot of scenarios expecting either GET or POST HTTP messages and I'd like to say, that it works perfectly fine;paramname = paramvalue
key-value mapping(s) alike (see POST Message Body types here);docs.spring.io
, an official source for Spring Documentation, clearly states, that:In Spring MVC, "request parameters" map to query parameters, form data, and parts in multipart requests.
So, the answer is YES, you can use @RequestParam
annotation with @Controller
class's method's parameter, as long as that method is a handler method (is request-mapped by @RequestMapping
) and you don't expect Object, this is perfectly legal and there's nothing wrong with it.
Upvotes: 45
Reputation: 11
public void createLeave(@RequestParam Map<String, String> requestParams)
Above code did not work.
Correct syntax is:
public void createLeave(@RequestBody Map<String, String> requestParams)
Which will map the request to a map
Upvotes: 0
Reputation: 185
You should use @RequestBody
instead of using @RequestParam
And you should provide whole object as a body of request
@RequestParam
is to get data from URL
you can do something like
public saveUser(@RequestBody User user) { do something with user }
and it will be mapped as User object for example
Upvotes: 2
Reputation: 141
@PostMapping("/createleave")
public void createLeave(@RequestParam Map<String, String> requestParams){
String start = requestParams.get("start");
String end= requestParams.get("end");
String hours= requestParams.get("hours");
String username = requestParams.get("username");
System.out.println("Entering createLeave " + start + " " + end + " " + hours + " " + username);
}
This is for multipart/form-data enctype post request.
Upvotes: -2
Reputation: 3787
What you are asking for is fundamentally wrong. POST requests sends data in a body payload, which is mapped via @RequestBody
. @RequestParam
is used to map data through the URL parameters such as /url?start=foo
. What you are trying to do is use @RequestParam
to do the job of @RequestBody
.
@RequestBody Map<String, String> payload
. Be sure to include 'Content-Type': 'application/json'
in your request header.@RequestParam
, use a GET request instead and send your data via URL parameters.@ModelAttribute
.@RequestBody Map<String, String> payload
. To do this, please see this answer.It is not possible to map form data encoded data directly to a Map<String, String>
.
Upvotes: 34