Request URL là một URL mà người dùng sẽ sử dụng để truy cập vào ứng dụng web của chúng ta. Trong bài viết này, chúng ta sẽ tìm hiểu làm thế nào để định nghĩa request URL cho controller trong Spring MVC các bạn nhé!
Định nghĩa request URL
Một controller có thể xử lý được một hoặc nhiều request với request URL khác nhau. Spring MVC cung cấp cho chúng ta annotation @RequestMapping để định nghĩa một request URL.
Trong ví dụ của bài viết trước, các bạn thấy controller HomeController đã được định nghĩa một request URL:
1 |
@RequestMapping(value = "/", method = RequestMethod.GET) |
Controller với 1 request URL
Nếu annotation @RequestMapping với request URL chỉ được định nghĩa bên trên định nghĩa của một lớp thì controller này chỉ xử lý cho một request duy nhất.
Ví dụ:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 |
package com.huongdanjava.springmvc; import java.text.DateFormat; import java.util.Date; import java.util.Locale; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.stereotype.Controller; import org.springframework.ui.Model; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; /** * Handles requests for the application home page. */ @Controller @RequestMapping(value = "/", method = RequestMethod.GET) public class HomeController { private static final Logger logger = LoggerFactory.getLogger(HomeController.class); /** * Simply selects the home view to render by returning its name. */ @RequestMapping public String home(Locale locale, Model model) { logger.info("Welcome home! The client locale is {}.", locale); Date date = new Date(); DateFormat dateFormat = DateFormat.getDateTimeInstance(DateFormat.LONG, DateFormat.LONG, locale); String formattedDate = dateFormat.format(date); model.addAttribute("serverTime", formattedDate ); return "home"; } } |
Trong trường hợp này, nếu chúng ta thêm một phương thức nữa với annotation @RequestMapping mà không có request URL:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 |
package com.huongdanjava.springmvc; import java.text.DateFormat; import java.util.Date; import java.util.Locale; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.stereotype.Controller; import org.springframework.ui.Model; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; /** * Handles requests for the application home page. */ @Controller @RequestMapping(value = "/", method = RequestMethod.GET) public class HomeController { private static final Logger logger = LoggerFactory.getLogger(HomeController.class); /** * Simply selects the home view to render by returning its name. */ @RequestMapping public String home(Locale locale, Model model) { logger.info("Welcome home! The client locale is {}.", locale); Date date = new Date(); DateFormat dateFormat = DateFormat.getDateTimeInstance(DateFormat.LONG, DateFormat.LONG, locale); String formattedDate = dateFormat.format(date); model.addAttribute("serverTime", formattedDate); return "home"; } @RequestMapping public String login() { return "login"; } } |
thì khi chạy chúng ta sẽ gặp lỗi ngay:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 |
Caused by: java.lang.IllegalStateException: Ambiguous mapping found. Cannot map 'homeController' bean method public java.lang.String com.huongdanjava.springmvc.HomeController.home(java.util.Locale,org.springframework.ui.Model) to {[/],methods=[GET],params=[],headers=[],consumes=[],produces=[],custom=[]}: There is already 'homeController' bean method public java.lang.String com.huongdanjava.springmvc.HomeController.login() mapped. at org.springframework.web.servlet.handler.AbstractHandlerMethodMapping.registerHandlerMethod(AbstractHandlerMethodMapping.java:183) at org.springframework.web.servlet.handler.AbstractHandlerMethodMapping.detectHandlerMethods(AbstractHandlerMethodMapping.java:147) at org.springframework.web.servlet.handler.AbstractHandlerMethodMapping.initHandlerMethods(AbstractHandlerMethodMapping.java:109) at org.springframework.web.servlet.handler.AbstractHandlerMethodMapping.initApplicationContext(AbstractHandlerMethodMapping.java:89) at org.springframework.context.support.ApplicationObjectSupport.initApplicationContext(ApplicationObjectSupport.java:119) at org.springframework.web.context.support.WebApplicationObjectSupport.initApplicationContext(WebApplicationObjectSupport.java:72) at org.springframework.context.support.ApplicationObjectSupport.setApplicationContext(ApplicationObjectSupport.java:73) at org.springframework.context.support.ApplicationContextAwareProcessor.invokeAwareInterfaces(ApplicationContextAwareProcessor.java:117) at org.springframework.context.support.ApplicationContextAwareProcessor.postProcessBeforeInitialization(ApplicationContextAwareProcessor.java:92) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.applyBeanPostProcessorsBeforeInitialization(AbstractAutowireCapableBeanFactory.java:394) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1448) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:519) ... 66 more |
Controller với nhiều request URL
Nếu annotation @RequestMapping với request URL được định nghĩa ở các phương thức thì controller này có thể xử lý nhiều request khác nhau.
Ví dụ sau lớp HomeController có thể xử lý 2 request đến từ người dùng bao gồm trang chủ và trang đăng nhập:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 |
package com.huongdanjava.springmvc; import java.text.DateFormat; import java.util.Date; import java.util.Locale; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.stereotype.Controller; import org.springframework.ui.Model; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; /** * Handles requests for the application home page. */ @Controller public class HomeController { private static final Logger logger = LoggerFactory.getLogger(HomeController.class); /** * Simply selects the home view to render by returning its name. */ @RequestMapping(value = "/", method = RequestMethod.GET) public String home(Locale locale, Model model) { logger.info("Welcome home! The client locale is {}.", locale); Date date = new Date(); DateFormat dateFormat = DateFormat.getDateTimeInstance(DateFormat.LONG, DateFormat.LONG, locale); String formattedDate = dateFormat.format(date); model.addAttribute("serverTime", formattedDate); return "home"; } @RequestMapping(value = "/login") public String login() { return "login"; } } |
Ngoài ra, các bạn cũng có thể định nghĩa một phương thức có thể xử lý được nhiều request bằng cách định nghĩa request URL như sau:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 |
package com.huongdanjava.springmvc; import java.text.DateFormat; import java.util.Date; import java.util.Locale; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.stereotype.Controller; import org.springframework.ui.Model; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; /** * Handles requests for the application home page. */ @Controller public class HomeController { private static final Logger logger = LoggerFactory.getLogger(HomeController.class); /** * Simply selects the home view to render by returning its name. */ @RequestMapping(value = { "/home", "/login", "/logout" }, method = RequestMethod.GET) public String home(Locale locale, Model model) { logger.info("Welcome home! The client locale is {}.", locale); Date date = new Date(); DateFormat dateFormat = DateFormat.getDateTimeInstance(DateFormat.LONG, DateFormat.LONG, locale); String formattedDate = dateFormat.format(date); model.addAttribute("serverTime", formattedDate); return "home"; } } |
Nối request URL
Trong trường hợp cả lớp và phương thức đều được khai báo với annotation @RequestMapping cùng với request URL thì request URL mà người dùng sử dụng để truy cập đến một trang nào đó phải là request URL của lớp cộng với request URL của phương thức.
Mình có ví dụ sau:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 |
package com.huongdanjava.springmvc; import java.text.DateFormat; import java.util.Date; import java.util.Locale; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.stereotype.Controller; import org.springframework.ui.Model; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; /** * Handles requests for the application home page. */ @Controller @RequestMapping("test") public class HomeController { private static final Logger logger = LoggerFactory.getLogger(HomeController.class); /** * Simply selects the home view to render by returning its name. */ @RequestMapping(value = "home", method = RequestMethod.GET) public String home(Locale locale, Model model) { logger.info("Welcome home! The client locale is {}.", locale); Date date = new Date(); DateFormat dateFormat = DateFormat.getDateTimeInstance(DateFormat.LONG, DateFormat.LONG, locale); String formattedDate = dateFormat.format(date); model.addAttribute("serverTime", formattedDate); return "home"; } } |
Trong ví dụ trên, mình đã khai báo annotation @RequestMapping cả trên lớp (“test”) và phương thức (“home”), thì request URL mà người dùng cần dùng để truy cập đến trang chủ phải là “/test/home”.
Kết quả:
AnBinh
Trong ví dụ cuối, “test” và “home” đều ko cần dấu / ở trước à anh? suy ra là Spring tự hiểu để thêm / vào url à?
Khanh Nguyễn
Đúng rồi đó em!