前言
Spring MVC是Spring構建在Servlet API上的Web框架。目前大部分的Java Web 開發已經使用Spring MVC 來做。它提供了模型 - 視圖 - 控制器架構,可用於開發靈活的Web應用程序。在本教程中,我們將重點關注與之相關的問題,因爲它通常是Spring開發人員面試的主題。
爲什麼選擇Spring MVC
Spring MVC 實現了一些明確而且相對低耦合的概念,可以讓開發者很容易開發和測試他們的Web應用。這些概念有:
- Dispatcher Servlet ——核心Servlet前置控制器,配置在web.xml文件中的。攔截匹配的請求,Servlet攔截匹配規則要自己定義,把攔截下來的請求,依據相應的規則分發到目標Controller來處理
- Controllers ——具體的業務控制器,處理具體請求的業務並響應
- View Resolvers ——視圖解析器,用於將響應的邏輯視圖解析爲真正的視圖View對象
- Views, Models ——Views的主要作用是用於處理響應視圖,然後返回給客戶端,Models主要用於傳遞控制方法處理數據到響應視圖頁面
- ModelAndView ——Model 和 View 的複合體
- Model and Session Attributes ——對模型屬性和會話屬性的處理
這些概念都是完全獨立而且職責單一。因此Spring MVC給了我們很大的靈活性。它基於接口(提供的實現類),我們可以使用自定義接口配置框架的每個部分。另一個重要的事情是我們不再依賴於特定的視圖技術(例如,JSP),可以選擇我們最複合業務的視圖技術。此外,我們不僅僅在Web應用程序開發中使用Spring MVC,也可以用它創建RESTful Web服務。
SpringMVC的流程
- 用戶發送請求至前端控制器DispatcherServlet;
- DispatcherServlet收到請求後,調用HandlerMapping處理器映射器,請求獲取Handle;
- 處理器映射器根據請求url找到具體的處理器,生成處理器對象及處理器攔截器(如果有)一併返回給DispatcherServlet;
- DispatcherServlet 調用 HandlerAdapter處理器適配器;
- HandlerAdapter 經過適配調用 具體處理器(Handler,也叫後端控制器);
- Handler執行完成返回ModelAndView;
- HandlerAdapter將Handler執行結果ModelAndView返回給DispatcherServlet;
- DispatcherServlet將ModelAndView傳給ViewResolver視圖解析器進行解析;
- ViewResolver解析後返回具體View;
- DispatcherServlet對View進行渲染視圖(即將模型數據填充至視圖中)
- DispatcherServlet響應用戶。
流程圖:
@Autowired 註解的規則是什麼
@Autowired
註解可以使用在成員屬性上或方法上,按類型注入Spring bean。這個註解允許Spring解析協作的bean並注入到你業務需要的bean中。
簡述一下註解ModelAttribute
@ModelAttribute
註解是Spring MVC中最重要的註解之一。它將方法參數或方法返回值綁定到命名中的Model屬性中,然後將其公開給Web視圖。如果我們在方法級別使用它,則表明該方法的目的是添加一個或多個模型屬性。另一方面,當用作方法參數時,它表示應從模型中檢索參數。如果不存在,我們應該首先實例化它,然後將其添加到Model中。一旦出現在模型中,我們應該填充所有具有匹配名稱的請求參數的參數字段。
@Controller和@RestController之間有什麼區別
@Controller
和@RestController
註釋之間的主要區別在於@ResponseBody
註釋自動包含在@RestController
中。這意味着我們不需要使用@ResponseBody
來註釋我們的處理程序方法。
描述一下 @PathVariable
我們可以使用@PathVariable
註解來從請求URI中提取一個特定模版變量的值來作爲我們的請求參數。例如 從/user/123
提取123
給/user/{id}
控制器來獲取一個id=123
的數據映射關係。需要特別指出的是通過此註解獲取的值不會被編碼。具體可通過我的文章來獲取原因。
如何在Spring MVC中校驗參數
Spring MVC 默認支持JSR-303校驗規範 。並在Spring-Boot-starter-web中提供了JSR-303規範實現Hibernate Validator。我們可以使用它來進行參數校驗。詳情可查看我的文章。
@RequestBody 和 @ResponseBody 是幹嘛用的
-
@RequestBody
註解用於控制器方法參數上,目的是將Http 請求體轉換爲領域對象(請求參數)。Spring 通過HttpMessageConverter
將請求體反序列化到Java對象中,默認使用jackson類庫反序列化。 -
@ResponseBody
註解使用於Spring MVC控制器中的處理程序方法上,它表明我們將把方法的返回類型直接寫入HTTP響應主體而不會將它放在Model中,同樣不會將其解釋爲視圖名稱。
Spring MVC 攔截器有什麼用怎麼用
Spring MVC攔截器允許我們攔截客戶端請求並在三個地方處理它 - 在處理之前,處理之後或完成之後(在呈現視圖時)。攔截器切面處理一些公共邏輯而避免重複處理程序代碼(如日誌記錄),也可以用來更改Spring模型中全局使用的參數。通過以下方式:
-
org.springframework.web.servlet.handler.HandlerInterceptorAdapter
——繼承該類 -
org.springframework.web.servlet.HandlerInterceptor
——實現該接口
如何全局處理控制器異常?
通過@ControllerAdvice
(也可使用@RestControllerAdvice
)註解和@ExceptionHandler
註解組合,通過在方法入參中捕獲異常進行處理,舉例如下:
@Slf4j
@RestControllerAdvice("cn.felord.manage.api")
public class GlobalExceptionControllerAdvice {
@ExceptionHandler(NullPointerException.class)
public Rest nullPointHandler(HttpServletRequest request, NullPointerException e) {
log.error("空指針啦,趕緊關注公衆號:Felordcn", e);
return RestBody.failure(-1, "null point exception");
}
}
如何處理Spring MVC 中的跨域問題?
Spring MVC 解決跨域問題主要有以下種辦法:
- 通過Spring MVC 攔截器來處理,同理servlet中的
filter
也可以處理。 - 通過在控制層方法使用
@CrossOrigin
註解。 請注意該方案需要在Spring MVC 4.x 以上。 - 通過在Spring MVC xml配置文件中的
<mvc:cors>
標籤中配置。 - 通過
WebMvcConfigurer#addCorsMappings(CorsRegistry)
來配置。
如果想具體深入可通過公衆號:Felordcn 來獲取具體的教程。
如何格式化Spring MVC如參參數?
一般可通過兩種方式:
- 實現
org.springframework.core.convert.converter.Converter<S,T>
,並將實現注入Spring容器中。 - 實現
org.springframework.format.Formatter<T>
,並將實現注入Spring 容器中。
關注公衆號:碼農小胖哥 獲取更多資訊