在早期 Java Web 的開發中,統一把顯示層、控制層、顯示層的操做所有交給 JSP 或者 Java Bean 來進行處理,存在必定的弊端,例如:JSP 和 Java Bean 之間嚴重耦合、開發效率低等弊端。javascript
Spring MVC 是 Spring 體系中的一員,提供「模型-視圖-控制器」(Model-View-Controller)架構和隨時可用的組件,用於開發靈活且鬆散耦合的 Web 應用程序。html
MVC 模式有助於分離應用程序的不一樣方面,如輸入邏輯,業務邏輯和 UI 邏輯,同時在全部這些元素之間提供鬆散耦合。java
Spring MVC 也是基於 Servlet 來處理請求的,主要經過 DispatcherServlet 這個 Servlet 來處理請求,處理過程須要經過九大組件來完成,先看到下面這個流程圖:python
Spring MVC 處理請求的流程大體如上圖所示web
DispatcherServlet
進行處理。DispatcherServlet
將該請求傳給了處理器映射組件 HandlerMapping
,並獲取到適合該請求的 HandlerExecutionChain 攔截器和處理器對象。DispatcherServlet
還不能直接調用處理器的邏輯,須要進行對處理器進行適配。處理器適配成功後,DispatcherServlet
經過處理器適配器 HandlerAdapter
調用處理器的邏輯,並獲取返回值 ModelAndView
對象。DispatcherServlet
須要根據 ModelAndView 解析視圖。解析視圖的工做由 ViewResolver
完成,若能解析成功,ViewResolver
會返回相應的 View 視圖對象。以上就是 Spring MVC 處理請求的全過程,上面的流程進行了必定的簡化,主要涉及到最核心的組件,還有許多其餘組件沒有表現出來,不過這並不影響你們對主過程的理解。面試
總結:客戶端發起請求後,最終會交由 DispatcherServlet 來處理,它會經過你的 URI 找到對應的方法,從請求中解析參數,而後經過反射機制調用該方法,將方法的執行結果設置到響應中,若是存在對應的 View 對象,則進行頁面渲染,實際上就是將請求轉發到指定的 URLspring
那麼接下來就簡單介紹一下 DispatcherServlet
和九大組件(按使用順序排序的):json
組件 | 說明 |
---|---|
DispatcherServlet | Spring MVC 的核心組件,是請求的入口,負責協調各個組件工做 |
MultipartResolver | 內容類型( Content-Type )爲 multipart/* 的請求的解析器,例如解析處理文件上傳的請求,便於獲取參數信息以及上傳的文件 |
HandlerMapping | 請求的處理器匹配器,負責爲請求找到合適的 HandlerExecutionChain 處理器執行鏈,包含處理器(handler )和攔截器們(interceptors ) |
HandlerAdapter | 處理器的適配器。由於處理器 handler 的類型是 Object 類型,須要有一個調用者來實現 handler 是怎麼被執行。Spring 中的處理器的實現多變,好比用戶處理器能夠實現 Controller 接口、HttpRequestHandler 接口,也能夠用 @RequestMapping 註解將方法做爲一個處理器等,這就致使 Spring MVC 沒法直接執行這個處理器。因此這裏須要一個處理器適配器,由它去執行處理器 |
HandlerExceptionResolver | 處理器異常解析器,將處理器( handler )執行時發生的異常,解析( 轉換 )成對應的 ModelAndView 結果 |
RequestToViewNameTranslator | 視圖名稱轉換器,用於解析出請求的默認視圖名 |
LocaleResolver | 本地化(國際化)解析器,提供國際化支持 |
ThemeResolver | 主題解析器,提供可設置應用總體樣式風格的支持 |
ViewResolver | 視圖解析器,根據視圖名和國際化,得到最終的視圖 View 對象 |
FlashMapManager | FlashMap 管理器,負責重定向時,保存參數至臨時存儲(默認 Session) |
Spring MVC 對各個組件的職責劃分的比較清晰。DispatcherServlet
負責協調,其餘組件則各自作份內之事,互不干擾。後端
@Controller
註解標記一個類爲 Spring Web MVC 控制器 Controller。Spring MVC 會將掃描到該註解的類,而後掃描這個類下面帶有 @RequestMapping
註解的方法,根據註解信息,爲這個方法生成一個對應的處理器對象,在上面的 HandlerMapping 和 HandlerAdapter組件中講到過。api
固然,除了添加 @Controller
註解這種方式之外,你還能夠實現 Spring MVC 提供的 Controller
或者 HttpRequestHandler
接口,對應的實現類也會被做爲一個處理器對象
@RequestMapping
註解,在上面已經講過了,配置處理器的 HTTP 請求方法,URI等信息,這樣才能將請求和方法進行映射。這個註解能夠做用於類上面,也能夠做用於方法上面,在類上面通常是配置這個控制器的 URI 前綴
@RestController
註解,在 @Controller
基礎上,增長了 @ResponseBody
註解,更加適合目前先後端分離的架構下,提供 Restful API ,返回例如 JSON 數據格式。固然,返回什麼樣的數據格式,根據客戶端的 ACCEPT
請求頭來決定。
@RequestMapping
:可註解在類和方法上;@GetMapping
僅可註冊在方法上
@RequestMapping
:可進行 GET、POST、PUT、DELETE 等請求方法;@GetMapping
是 @RequestMapping
的 GET 請求方法的特例,目的是爲了提升清晰度。
兩個註解都用於方法參數,獲取參數值的方式不一樣,@RequestParam
註解的參數從請求攜帶的參數中獲取,而 @PathVariable
註解從請求的 URI 中獲取
可使用 @ResponseBody
註解,或者使用包含 @ResponseBody
註解的 @RestController
註解。
固然,仍是須要配合相應的支持 JSON 格式化的 HttpMessageConverter 實現類。例如,Spring MVC 默認使用 MappingJackson2HttpMessageConverter
WebApplicationContext 是實現 ApplicationContext 接口的子類,專門爲 WEB 應用準備的
入口不一樣
配置映射不一樣,
視圖不一樣
Spring MVC 攔截器有三個加強處理的地方:
能夠經過攔截器進行權限檢驗,參數校驗,記錄日誌等操做
有如下幾點:
通常拓展性好的框架,都會提供相應的攔截器或過濾器機制,方便的開發人員作一些拓展
REST 表明着抽象狀態轉移,它是根據 HTTP 協議從客戶端發送數據到服務端,例如:服務端的一本書能夠以 XML 或 JSON 格式傳遞到客戶端
然而,假如你不熟悉REST,我建議你先看看 REST API design and development 這篇文章來更好的瞭解它。也能夠閱讀知乎上的 《怎樣用通俗的語言解釋 REST,以及 RESTful?》 討論
資源是指數據在 REST 架構中如何顯示的。將實體做爲資源公開 ,它容許客戶端經過 HTTP 方法如:GET, POST,PUT, DELETE 等讀,寫,修改和建立資源
REST 接口是經過 HTTP 方法完成操做
因此,是否安全的界限,在於是否修改服務端的資源
有一些 HTTP 方法,如:GET,無論你使用多少次它都能產生相同的結果,在沒有任何一邊影響的狀況下,發送多個 GET 請求到相同的URI 將會產生相同的響應結果。所以,這就是所謂冪等操做
換句話說,POST方法不是冪等操做 ,由於若是發送多個 POST 請求,它將在服務端建立不一樣的資源。可是,假如你用 PUT 更新資源,它將是冪等操做。
甚至多個 PUT 請求被用來更新服務端資源,將獲得相同的結果
是的,REST 是可擴展的和可協做的。它既不託管一種特定的技術選擇,也不定在客戶端或者服務端。你能夠用 Java, C++, Python, 或 JavaScript 來建立 RESTful Web 服務,也能夠在客戶端使用它們。
我建議你讀一本關於REST接口的書來了解更多,如:RESTful Web Services 。
因此這裏的「可拓展」、「協同」對應到咱們平時常說的,「跨語言」、「語言無關」
REST 能用任何的 HTTP 方法,可是,最受歡迎的是:
剛好,這四個操做,對上咱們平常邏輯的 CRUD 操做
在刪除成功以後,您的 REST API 應該返回什麼狀態代碼,並無嚴格的規則。它能夠返回 200 或 204 沒有內容
是的,REST API 應該是無狀態的,由於它是基於 HTTP 的,它也是無狀態的
REST API 中的請求應該包含處理它所需的全部細節。它不該該依賴於之前或下一個請求或服務器端維護的一些數據,例如會話
REST 規範爲使其無狀態設置了一個約束,在設計 REST API 時,你應該記住這一點
安全是一個寬泛的術語。它可能意味着消息的安全性,這是經過認證和受權提供的加密或訪問限制提供的
REST 一般不是安全的,須要開發人員本身實現安全機制