SpringBoot中處理異常的方法有哪些,相信很多沒有經(jīng)驗的人對此束手無策,為此本文總結(jié)了問題出現(xiàn)的原因和解決方法,通過這篇文章希望你能解決這個問題。
十余年的滎陽網(wǎng)站建設經(jīng)驗,針對設計、前端、開發(fā)、售后、文案、推廣等六對一服務,響應快,48小時及時工作處理。成都全網(wǎng)營銷的優(yōu)勢是能夠根據(jù)用戶設備顯示端的尺寸不同,自動調(diào)整滎陽建站的顯示方式,使網(wǎng)站能夠適用不同顯示終端,在瀏覽器中調(diào)整網(wǎng)站的寬度,無論在任何一種瀏覽器上瀏覽網(wǎng)站,都能展現(xiàn)優(yōu)雅布局與設計,從而大程度地提升瀏覽體驗。創(chuàng)新互聯(lián)從事“滎陽網(wǎng)站設計”,“滎陽網(wǎng)站推廣”以來,每個客戶項目都認真落實執(zhí)行。
1. 新建異常信息實體類
非必要的類,主要用于包裝異常信息。
src/main/java/com/twuc/webApp/exception/ErrorResponse.java
/** * @author shuang.kou */ public class ErrorResponse { private String message; private String errorTypeName; public ErrorResponse(Exception e) { this(e.getClass().getName(), e.getMessage()); } public ErrorResponse(String errorTypeName, String message) { this.errorTypeName = errorTypeName; this.message = message; } ......省略getter/setter方法 }
2. 自定義異常類型
src/main/java/com/twuc/webApp/exception/ResourceNotFoundException.java
一般我們處理的都是 RuntimeException ,所以如果你需要自定義異常類型的話直接集成這個類就可以了。
/** * @author shuang.kou * 自定義異常類型 */ public class ResourceNotFoundException extends RuntimeException { private String message; public ResourceNotFoundException() { super(); } public ResourceNotFoundException(String message) { super(message); this.message = message; } @Override public String getMessage() { return message; } public void setMessage(String message) { this.message = message; } }
3. 新建異常處理類
我們只需要在類上加上@ControllerAdvice注解這個類就成為了全局異常處理類,當然你也可以通過 assignableTypes指定特定的 Controller 類,讓異常處理類只處理特定類拋出的異常。
src/main/java/com/twuc/webApp/exception/GlobalExceptionHandler.java
/** * @author shuang.kou */ @ControllerAdvice(assignableTypes = {ExceptionController.class}) @ResponseBody public class GlobalExceptionHandler { ErrorResponse illegalArgumentResponse = new ErrorResponse(new IllegalArgumentException("參數(shù)錯誤!")); ErrorResponse resourseNotFoundResponse = new ErrorResponse(new ResourceNotFoundException("Sorry, the resourse not found!")); @ExceptionHandler(value = Exception.class)// 攔截所有異常, 這里只是為了演示,一般情況下一個方法特定處理一種異常 public ResponseEntityexceptionHandler(Exception e) { if (e instanceof IllegalArgumentException) { return ResponseEntity.status(400).body(illegalArgumentResponse); } else if (e instanceof ResourceNotFoundException) { return ResponseEntity.status(404).body(resourseNotFoundResponse); } return null; } }
4. controller模擬拋出異常
src/main/java/com/twuc/webApp/web/ExceptionController.java
/** * @author shuang.kou */ @RestController @RequestMapping("/api") public class ExceptionController { @GetMapping("/illegalArgumentException") public void throwException() { throw new IllegalArgumentException(); } @GetMapping("/resourceNotFoundException") public void throwException2() { throw new ResourceNotFoundException(); } }
使用 Get 請求 localhost:8080/api/resourceNotFoundException[1] (curl -i -s -X GET url),服務端返回的 JSON 數(shù)據(jù)如下:
{ "message": "Sorry, the resourse not found!", "errorTypeName": "com.twuc.webApp.exception.ResourceNotFoundException" }
5. 編寫測試類
MockMvc 由org.springframework.boot.test包提供,實現(xiàn)了對Http請求的模擬,一般用于我們測試 controller 層。
/** * @author shuang.kou */ @AutoConfigureMockMvc @SpringBootTest public class ExceptionTest { @Autowired MockMvc mockMvc; @Test void should_return_400_if_param_not_valid() throws Exception { mockMvc.perform(get("/api/illegalArgumentException")) .andExpect(status().is(400)) .andExpect(jsonPath("$.message").value("參數(shù)錯誤!")); } @Test void should_return_404_if_resourse_not_found() throws Exception { mockMvc.perform(get("/api/resourceNotFoundException")) .andExpect(status().is(404)) .andExpect(jsonPath("$.message").value("Sorry, the resourse not found!")); } }
二、 @ExceptionHandler 處理 Controller 級別的異常
我們剛剛也說了使用@ControllerAdvice注解 可以通過 assignableTypes指定特定的類,讓異常處理類只處理特定類拋出的異常。所以這種處理異常的方式,實際上現(xiàn)在使用的比較少了。
我們把下面這段代碼移到 src/main/java/com/twuc/webApp/exception/GlobalExceptionHandler.java 中就可以了。
@ExceptionHandler(value = Exception.class)// 攔截所有異常 public ResponseEntityexceptionHandler(Exception e) { if (e instanceof IllegalArgumentException) { return ResponseEntity.status(400).body(illegalArgumentResponse); } else if (e instanceof ResourceNotFoundException) { return ResponseEntity.status(404).body(resourseNotFoundResponse); } return null; }
三、 ResponseStatusException
研究 ResponseStatusException 我們先來看看,通過 ResponseStatus注解簡單處理異常的方法(將異常映射為狀態(tài)碼)。
src/main/java/com/twuc/webApp/exception/ResourceNotFoundException.java
@ResponseStatus(code = HttpStatus.NOT_FOUND) public class ResourseNotFoundException2 extends RuntimeException { public ResourseNotFoundException2() { } public ResourseNotFoundException2(String message) { super(message); } }
src/main/java/com/twuc/webApp/web/ResponseStatusExceptionController.java
@RestController @RequestMapping("/api") public class ResponseStatusExceptionController { @GetMapping("/resourceNotFoundException2") public void throwException3() { throw new ResourseNotFoundException2("Sorry, the resourse not found!"); } }
使用 Get 請求 localhost:8080/api/resourceNotFoundException2[2] ,服務端返回的 JSON 數(shù)據(jù)如下:
{ "timestamp": "2019-08-21T07:11:43.744+0000", "status": 404, "error": "Not Found", "message": "Sorry, the resourse not found!", "path": "/api/resourceNotFoundException2" }
這種通過 ResponseStatus注解簡單處理異常的方法是的好處是比較簡單,但是一般我們不會這樣做,通過ResponseStatusException會更加方便,可以避免我們額外的異常類。
@GetMapping("/resourceNotFoundException2") public void throwException3() { throw new ResponseStatusException(HttpStatus.NOT_FOUND, "Sorry, the resourse not found!", new ResourceNotFoundException()); }
使用 Get 請求 localhost:8080/api/resourceNotFoundException2[3] ,服務端返回的 JSON 數(shù)據(jù)如下,和使用 ResponseStatus 實現(xiàn)的效果一樣:
{ "timestamp": "2019-08-21T07:28:12.017+0000", "status": 404, "error": "Not Found", "message": "Sorry, the resourse not found!", "path": "/api/resourceNotFoundException3" }
ResponseStatusException 提供了三個構造方法:
public ResponseStatusException(HttpStatus status) { this(status, null, null); } public ResponseStatusException(HttpStatus status, @Nullable String reason) { this(status, reason, null); } public ResponseStatusException(HttpStatus status, @Nullable String reason, @Nullable Throwable cause) { super(null, cause); Assert.notNull(status, "HttpStatus is required"); this.status = status; this.reason = reason; }
構造函數(shù)中的參數(shù)解釋如下:
status :http status
reason :response 的消息內(nèi)容
cause :拋出的異常
看完上述內(nèi)容,你們掌握SpringBoot中處理異常的方法有哪些的方法了嗎?如果還想學到更多技能或想了解更多相關內(nèi)容,歡迎關注創(chuàng)新互聯(lián)行業(yè)資訊頻道,感謝各位的閱讀!