Spring中@ControllerAdvice注解的用法解析
@ControllerAdvice 用法
顧名思義,@ControllerAdvice就是@Controller 的增強(qiáng)版。
@ControllerAdvice主要用來處理全局?jǐn)?shù)據(jù),一般搭配@ExceptionHandler、@ModelAttribute以及@InitBinder使用。
全局異常處理
@ControllerAdvice最常見的使用場景就是全局異常處理。
比如文件上傳大小限制的配置,如果用戶上傳的文件超過了限制大小,就會(huì)拋出異常,此時(shí)可以通過@ControllerAdvice結(jié)合@ExceptionHandler定義全局異常捕獲機(jī)制,代碼如下:
@ControllerAdvice
public class CustomExceptionHandler {
@ExceptionHandler(MaxUploadSizeExceededException.class)
public void uploadException(MaxUploadSizeExceededException e, HttpServletResponse resp) throws IOException {
resp.setContentType("text/html;charset=utf-8");
System.out.println(1111);
PrintWriter out = resp.getWriter();
out.write("上傳文件大小超出限制!");
out.flush();
out.close();
}
}只需在系統(tǒng)中定義CustomExceptionHandler類,然后添加@ControllerAdvice注解即可。當(dāng)系統(tǒng)啟動(dòng)時(shí),該類就會(huì)被掃描到Spring容器中,然后定義uploadException方法,在該方法上添加了@ExceptionHandler注解,其中定義的MaxUploadSizeExceededException.class 表明該方法用來處理MaxUploadSizeExceededException類型的異常。如果想讓該方法處理所有類型的異常,只需將MaxUploadSizeExceededException改為 Exception即可。方法的參數(shù)可以有異常實(shí)例、HttpServletResponse以及HttpServletRequest、Model 等,返回值可以是一段JSON、一個(gè)ModelAndView、一個(gè)邏輯視圖名等。此時(shí),上傳一個(gè)超大文件會(huì)有錯(cuò)誤提示給用戶。

如果返回參數(shù)是一個(gè)ModelAndView,假設(shè)使用的頁面模板為Thymeleaf(注意添加Thymeleaf相關(guān)依賴),此時(shí)異常處理方法定義如下:
@ControllerAdvice
public class CustomExceptionHandler {
@ExceptionHandler(MaxUploadSizeExceededException.class)
public ModelAndView uploadException(MaxUploadSizeExceededException e) throws IOException {
ModelAndView mv = new ModelAndView();
mv.addObject("msg", "上傳文件大小超出限制! ");
mv.setViewName("error");
return mv;
}
}然后在resources/templates目錄下創(chuàng)建error.html文件,內(nèi)容如下:
<!DOCTYPE html>
<html lang="en" xmlns:th="http://www.thymeleaf.org">
<head>
<meta charset="UTF-8">
<title>Title</title></head>
<body>
<div th:text="${msg}"></div>
</body>
</html>此時(shí)上傳出錯(cuò)效果一致。
添加全局?jǐn)?shù)據(jù)
@ControllerAdvice是一個(gè)全局?jǐn)?shù)據(jù)處理組件,因此也可以在@ControllerAdvice中配置全局?jǐn)?shù)據(jù),使用@ModelAttribute注解進(jìn)行配置,代碼如下:
@ControllerAdvice
public class GlobalConfig {
@ModelAttribute(value = "info")
public Map<String, String> userInfo() {
HashMap<String, String> map = new HashMap<>();
map.put("username", "羅貫中");
map.put("gender", "男");
return map;
}
}代碼解釋:
- 在全局配置中添加userInfo方法,返回一個(gè)map。該方法有一個(gè)注解@ModelAttribute,其中的value屬性表示這條返回?cái)?shù)據(jù)的key,而方法的返回值是返回?cái)?shù)據(jù)的value。
- 此時(shí)在任意請求的Controller 中,通過方法參數(shù)中的Model都可以獲取info 的數(shù)據(jù)。
Controller 例代碼如下:
public class MyController {
@GetMapping("/hello")
@ResponseBody
public void hello(Model model) {
Map<String, Object> map = model.asMap();
Set<String> keySet = map.keySet();
Iterator<String> iterator = keySet.iterator();
while (iterator.hasNext()) {
String key = iterator.next();
Object value = map.get(key);
System.out.println(key + ">>>>>" + value);
}
}
}在請求方法中,將Model 中的數(shù)據(jù)打印出來,如圖所示。

請求參數(shù)預(yù)處理
@ControllerAdvice結(jié)合@InitBinder還能實(shí)現(xiàn)請求參數(shù)預(yù)處理,即將表單中的數(shù)據(jù)綁定到實(shí)體類上時(shí)進(jìn)行一些額外處理。
例如有兩個(gè)實(shí)體類 Book和 Author,代碼如下:
@Data
@AllArgsConstructor
@NoArgsConstructor
@Component
@ToString
public class Book {
private String name;
private String author;
@JsonIgnore//一般標(biāo)記在屬性或者方法上,返回的json數(shù)據(jù)即不包含該屬性
private Float price;
@JsonFormat(pattern = "yyyy-MM-dd")
private Date publicationDate;
}
@Data
@AllArgsConstructor
@NoArgsConstructor
@ToString
public class Author {
private String name;
private int age;
}在 Controller 上需要接收兩個(gè)實(shí)體類的數(shù)據(jù),Controller 中的方法定義如下:
@ControllerAdvice
public class GlobalConfig1 {
@InitBinder("b")
public void init(WebDataBinder binder) {
binder.setFieldDefaultPrefix("b.");
}
@InitBinder("a")
public void init2(WebDataBinder binder) {
binder.setFieldDefaultPrefix("a.");
}
}代碼解釋:
- 在 GlobalConfig類中創(chuàng)建兩個(gè)方法,第一個(gè)@InitBinder(“b”)表示該方法是處理@ModelAttribute(“b”)對應(yīng)的參數(shù)的,第二個(gè)@InitBinder(“a”)表示該方法是處理@ModelAttribute(“a”)對應(yīng)的參數(shù)的。
- 在每個(gè)方法中給相應(yīng)的 Field設(shè)置一個(gè)前綴,然后在瀏覽器中請求http:/ocalhost:8080/book?b.name=三國演義&b.author=羅貫中&a.name=曹雪芹&a.age=48,即可成功地區(qū)分出name屬性。
- 在WebDataBinder對象中,還可以設(shè)置允許的字段、禁止的字段、必填字段以及驗(yàn)證器等。
ld設(shè)置一個(gè)前綴,然后在瀏覽器中請求/ocalhost:8080/book?b.name=三國演義&b.author=羅貫中&a.name=曹雪芹&a.age=48,即可成功地區(qū)分出name屬性。
在WebDataBinder對象中,還可以設(shè)置允許的字段、禁止的字段、必填字段以及驗(yàn)證器等。

到此這篇關(guān)于Spring中@ControllerAdvice注解的用法解析的文章就介紹到這了,更多相關(guān)@ControllerAdvice注解的用法內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!
相關(guān)文章
SpringBoot整合mybatis-generator-maven-plugin的方法
這篇文章主要介紹了SpringBoot整合mybatis-generator-maven-plugin,本文通過實(shí)例代碼給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2020-11-11
Java編程中使用XFire框架調(diào)用WebService程序接口
這篇文章主要介紹了Java編程中使用XFire調(diào)用WebService程序接口的方法,WebService是一種跨編程語言和跨操作系統(tǒng)平臺(tái)的遠(yuǎn)程調(diào)用技術(shù),需要的朋友可以參考下2015-12-12
java 過濾器模式(Filter/Criteria Pattern)詳細(xì)介紹
這篇文章主要介紹了java 過濾器模式(Filter/Criteria Pattern)詳細(xì)介紹的相關(guān)資料,需要的朋友可以參考下2016-10-10
mybatis實(shí)現(xiàn)對數(shù)據(jù)的增刪查改實(shí)例詳解
這篇文章主要介紹了mybatis實(shí)現(xiàn)對數(shù)據(jù)的增刪查改實(shí)例詳解的相關(guān)資料,非常不錯(cuò),具有參考借鑒價(jià)值,需要的朋友可以參考下2016-07-07

