寫在前面
🛫更多知識總結見SpringBoot 2專欄
🚕本篇知識點總結自尚硅谷雷神的視頻
🚒博主對于該知識尚在學習階段
🚄如果發現存在問題請毫不吝嗇的指出
🚀🚀扎哇太棗糕的博客首頁🚀🚀
文章目錄
- 1 異常處理
- 1.1 異常處理之錯誤頁面
- 1.2 異常處理之精確捕獲
- 1.3 異常處理之自定義異常
- 1.3 異常處理之框架底層異常
- 2 web原生組件的注入
- 2.1 servlet組件
- 2.2 filter組件
- 2.3 listener組件
- 3 web實現定制化總結
1 異常處理
??默認情況下,SpringBoot會提供/error處理所有的錯誤請求并返回相應的信息,對于瀏覽器客戶端來說會返回一個包含時間戳、狀態碼、錯誤信息、攜帶的自定義異常信息、發生錯誤的路徑等信息的錯誤Whitelabel頁面,對于機器客戶端(postman等)會返回一個包含以上內容的JSON數據
1.1 異常處理之錯誤頁面
??要想替代之前瀏覽器客戶端返回的錯誤Whitelabel頁面,需要將自定義的html頁面放在靜態資源static等的error文件夾下或者模板引擎templates的error文件夾下,這樣的話出現錯誤時SpringBoot發送/error請求就會自動解析這些頁面進行渲染。頁面解析規則:先將狀態碼的值與error文件夾下的頁面名進行精確匹配,如果精確匹配不到的話就按照4xx、5xx這樣的方式進行模糊匹配,要是還匹配不到的話就返回Whitelabel頁面
1.2 異常處理之精確捕獲
??要是說錯誤頁面是按照狀態碼進行頁面處理的話,精確捕獲就是通過異常類進行捕獲,捕獲之后再進行一系列的自定義操作。具體步驟就是:創建一個異常處理器類,并在類上加@ControllerAdvice注解表明是一個異常處理器并向容器中注冊該組件,@ExceptionHandler注解對參數中的異常類進行精準捕獲,并在方法體定義具體的處理操作。
@Slf4j
@ControllerAdvice
public class GlobalExceptionHandler {@ExceptionHandler({ArithmeticException.class, NullPointerException.class})public String handleArithException(Exception e) {log.info("系統捕獲到異常信息:{}", e);return "login";}
}
1.3 異常處理之自定義異常
??有時候我們需要在程序中自定義一些運行時異常,這些異常并不會像那些異常一樣產生異常狀態碼,甚至在未定義之前都不算是異常且不會影響程序的正常運行。這時就需要我們自定義異常的產生邏輯,并自定義異常類創建有參無參構造器,在類上加@ResponseStatus注解,使用注解參數定義異常響應碼和異常信息
@ResponseStatus(value = HttpStatus.FORBIDDEN, reason = "用戶數量太多")
public class UserTooManyException extends RuntimeException{public UserTooManyException() {}public UserTooManyException(String message) {super(message);}
}
異常產生邏輯:
// 判斷用戶數量拋出用戶數量過多的自定義異常
if (users.size() > 3) {throw new UserTooManyException();
}
1.3 異常處理之框架底層異常
??除了exception類中定義的異常外,spring框架底層也定義了一些異常,這些異常由DefaultHandlerExceptionResolver來處理
2 web原生組件的注入
2.1 servlet組件
??servlet組件需要自定義創建一個servlet類繼承HttpServlet,并使用@WebServlet注解的urlPatterns屬性聲明攔截的請求,再通過主程序類上使用@ServletComponentScan(basePackages = “…”)注解將該組件掃描注冊到容器中。
// 聲明攔截的請求
@WebServlet(urlPatterns = "/my")
public class MyServlet extends HttpServlet {@Overrideprotected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {resp.getWriter().write("385695");}
}
2.2 filter組件
??filter組件需要自定義創建一個filter類實現Filter接口,并使用@WebFilter注解的urlPatterns屬性聲明過濾的請求
@Slf4j
@WebFilter(urlPatterns = {"/css/*", "/images/*"})
public class MyFilter implements Filter {@Overridepublic void init(FilterConfig filterConfig) throws ServletException {log.info("MyFilter初始化……");}@Overridepublic void doFilter(ServletRequest servletRequest, ServletResponse servletResponse, FilterChain filterChain) throws IOException, ServletException {log.info("MyFilter方法開始工作了……");filterChain.doFilter(servletRequest, servletResponse);}@Overridepublic void destroy() {log.info("MyFilter銷毀了……");}
}
2.3 listener組件
??listener組件需要自定義創建一個listener類實現ServletContextListener 接口,并使用@WebListener注解
@Slf4j
@WebListener
public class MyServletContextListener implements ServletContextListener {@Overridepublic void contextInitialized(ServletContextEvent sce) {log.info("MyServletContextListener監聽到項目初始化完成……");}@Overridepublic void contextDestroyed(ServletContextEvent sce) {log.info("MyServletContextListener監聽到項目已經銷毀……");}
}
除了使用注解進行注冊之外,還可以使用配置類的方式將以上三種組件注冊到容器中去
@Configuration
public class MyRegistConfig {@Beanpublic ServletRegistrationBean MyServlet() {MyServlet myServlet = new MyServlet();return new ServletRegistrationBean(myServlet, "/my", "/my02");}@Beanpublic FilterRegistrationBean myFilter() {MyFilter myFilter = new MyFilter();FilterRegistrationBean filterRegistrationBean = new FilterRegistrationBean(myFilter);filterRegistrationBean.setUrlPatterns(Arrays.asList("/my", "/my02"));return filterRegistrationBean;}@Beanpublic ServletListenerRegistrationBean myListener() {MyServletContextListener listener = new MyServletContextListener();return new ServletListenerRegistrationBean(listener);}
}
??通過servlet組件聲明的/my請求并不會經過spring的攔截器攔截處理,而是直接交由tomcat服務器進行處理:現在有這么兩個組件攔截到我們發送的/my請求,一個是spring的組件DispatcherServlet通過/路徑攔截到,一個是tomcat的自定義MyServlet組件通過/my路徑攔截到。tomcat服務器對請求有這么一個處理規則,當多個servlet組件都能處理到同一個請求的時候,使用匹配度最高的組件進行處理,也就是說處理請求的是tomcat的MyServlet組件。
3 web實現定制化總結
- 創建配置類實現WebMvcConfigurer接口,重寫相應的方法或者使用@Bean注解向容器中擴展功能(使用的最多)
- 自定義配置類使用@Bean注解使用自定義的web原生組件替換容器中的默認組件或者向容器中添加組件
- 配置文件的配置項修改
- xxxCustomizer
- @EnableWebMvc注解表示全面接管SpringMVC,導致的效果就是SpringBoot的所有自動配置全部失效,全部功能都需要自己進行配置。大佬專屬注解,小白的禁術!!!