There are different ways in which user request parameters can be handled. We shall be taking the example of the signup form to understand the following concepts related to the most common ways of handling request parameters:
- Using the
RequestParam
annotation: This is used to bind the method parameters to web request parameters - Using the
RequestBody
annotation: This is used to bind the method parameter to the body of the web request - Using the
PathVariable
annotation: This is used to bind the method parameter to the URI template variable
In this section, we will learn how to use the RequestParam
annotation for reading web request parameters in the controller
class. The following image shows what the signup form looks like with three input fields such as Nick Name
, Email address,
and Password
:
Figure: New User Signup form
On submission of the preceding form, the user request parameters will be handled using the @RequestParam
annotation. The RequestParam
annotation is used to bind a method parameter to a web request parameter. The following code displays the binding of method parameters such as nickname
, emailAddress
, and password
with web request parameters such as nickname
, emailaddress
, and password
respectively. In simple words, the frontend has to send parameters with keys as nickname, email address, and password for the code given next to work.
@Controller @RequestMapping("/account/*") public class UserAccountController { @GetMapping("/signup") public String signup() { return "signup"; } @PostMapping("/signup/process") public String processSignup(ModelMap model, @RequestParam("nickname") String nickname, @RequestParam("emailaddress") String emailAddress, @RequestParam("password") String password) { model.addAttribute("login", true); model.addAttribute("nickname", nickname); return "index"; } }
In this section, we will learn when and how to use the RequestBody
annotation (@RequestBody
) for handling web requests.
The RequestBody
annotation is used to bind the method parameter with the body of the incoming request. In the process of binding, HttpMessageConverters
converts the body of the request appropriately (most commonly into the parameter object) based on the content type of the request.
The RequestBody
annotation is most commonly used in scenarios dealing with REST APIs.
The following example demonstrates the usage of the @RequestBody
annotation using a domain object, User
, which is made a parameter to the controller
method:
@RestController public class RestDemoController { @PostMapping("/hello") public HelloMessage getHelloMessage(@RequestBodyUser user) { HelloMessage helloMessage = new HelloMessage(); String name = user.getName(); helloMessage.setMessage( "Hello " + name + "! How are you doing?"); helloMessage.setName(name); return helloMessage; } }
In the preceding example, note some of the following:
- The
@PostMapping
annotation maps the REST API endpoint,/hello
, with the handler method,getHelloMessage
. Recall that@PostMapping
is a composed annotation which acts as a shortcut for@RequestMapping (method = RequestMethod.POST)
. - The
@RequestBody
annotation is used with theUser
object. This binds (or maps) the method parameter, user of typeUser
, with the body of the web request. The body of the request arrives in the following JSON format:
{"name": "Calvin Hobbes"}
The HttpMessageConverter
method converts the preceding into the User
object, whose code looks like the following:
public class User { private String name; public String getName() { return name; } public void setName(String name) { this.name = name; } }
- The
@RestController
annotation, a convenient annotation, which is itself annotated with@Controller
and@ResponseBody
annotations, and is used for programming REST API integration endpoints. - The
HelloMessage
class is returned as a response. The following is the code forHelloMessage
:
public class HelloMessage { private String message; private String name; public String getMessage() { return message; } public void setMessage(String message) { this.message = message; } public String getName() { return name; } public void setName(String name) { this.name = name; } }
The HttpMessageConverter
method converts the preceding response object into the following response message:
{"message": "message text goes here...", "name": "name goes here..."}
In this section, we will learn how to use the PathVariable
annotation for handling request parameters.
The PathVariable
annotation is used to bind a method parameter to a URI template variable. A URI template is a URI-like string containing one or more variables. For example, in the following code, /{nickname}
is a URI template consisting of nickname
as a variable. A method can have multiple @Pathvariable
annotations to bind multiple variables present in the URI template. PathVariable
is seen to be mainly used in the REST web service. Later, while going through Angular chapters, you will see that PathVariable
is very similar to handling routing parameters using the ActivatedRoute
concept:
@Controller @SpringBootApplication public class HealthAppApplication { @RequestMapping("/") public String home() { return "index"; } @GetMapping("/{nickname}") public String home(ModelMap model, @PathVariable String nickname) { model.addAttribute("name", nickname); return "index"; } public static void main(String[] args) { SpringApplication.run(HealthAppApplication.class, args); } }
Both RequestParam
and PathVariable
can be used to read the request parameters. @RequestParam
is used to retrieve the query parameters from the request URL. On the other hand, @PathVariable
is used to retrieve one or more placeholders from the URI. URLs without query parameters, for example, paths, tend to be cached. The following code demonstrates the usage of both RequestParam
and PathVariable
. Different URLs will be handled using different methods represented in the code as follows:
- URL (
http://localhost:8080, localhost:8080/?name=calvin
): This URL consists of a parameter such as name. The value of this parameter is obtained usingRequestParam
. Note that asrequired = false
is declared with the@RequestParam
definition in the code example given next, thus, a request URL such ashttp://localhost:8080/
would also get mapped to theusingRequestParam
method. - URI (
http://localhost:8080/calvin
): This URL consists of a name which can be handled using a placeholder variable whose value can be obtained using thePathVariable
method.
The following code displays the usage of both RequestParam
and PathVariable
:
@Controller @SpringBootApplication public class HealthAppApplication { // // RequestParam is used to retrieve value of parameter, name. // @RequestMapping("/") public String usingRequestParam(Model model, @RequestParam(value="name", required=false) String nickname) { model.addAttribute("nickname", nickname); return "index"; } @RequestMapping("/{nickname}") public String usingPathVariable(Model model, @PathVariable String nickname) { model.addAttribute("nickname", nickname); return "index"; } }
In the next section, you will learn how to use interceptors to handle web requests-response, before and after the requests are handled by the controller respectively.