SpringBoot與SpringMVC的關(guān)系分不清?全面解析理卑!看完這個(gè)就夠了

點(diǎn)關(guān)注翘紊,不迷路;持續(xù)更新Java架構(gòu)相關(guān)技術(shù)及資訊熱文C赀搿7薄!

spring boot就是一個(gè)大框架里面包含了許許多多的東西宇立,其中spring就是最核心的內(nèi)容之一踪宠,當(dāng)然就包含spring mvc。spring mvc 是只是spring 處理web層請(qǐng)求的一個(gè)模塊泄伪。因此他們的關(guān)系大概就是這樣:spring mvc < spring <springboot殴蓬。

理清SpringBoot與SpringMVC的關(guān)系

Spring 框架就像一個(gè)家族,有眾多衍生產(chǎn)品例如 boot蟋滴、security、jpa等等痘绎。但他們的基礎(chǔ)都是Spring 的 ioc和 aop ioc 提供了依賴注入的容器 aop 津函,解決了面向橫切面的編程,然后在此兩者的基礎(chǔ)上實(shí)現(xiàn)了其他延伸產(chǎn)品的高級(jí)功能孤页。

Spring MVC是基于 Servlet 的一個(gè) MVC 框架 主要解決 WEB 開(kāi)發(fā)的問(wèn)題尔苦,因?yàn)?Spring 的配置非常復(fù)雜,各種XML行施、 JavaConfig允坚、hin處理起來(lái)比較繁瑣。

于是為了簡(jiǎn)化開(kāi)發(fā)者的使用蛾号,從而創(chuàng)造性地推出了Spring boot稠项,約定優(yōu)于配置,簡(jiǎn)化了spring的配置流程鲜结。

說(shuō)得更簡(jiǎn)便一些:Spring 最初利用“工廠模式”(DI)和“代理模式”(AOP)解耦應(yīng)用組件展运。

大家覺(jué)得挺好用,于是按照這種模式搞了一個(gè) MVC框架(一些用Spring 解耦的組件)精刷,用開(kāi)發(fā) web 應(yīng)用( SpringMVC )拗胜。

然后有發(fā)現(xiàn)每次開(kāi)發(fā)都寫(xiě)很多樣板代碼,為了簡(jiǎn)化工作流程怒允,于是開(kāi)發(fā)出了一些“懶人整合包”(starter)埂软,這套就是 Spring Boot。

Spring MVC的功能Spring MVC提供了一種輕度耦合的方式來(lái)開(kāi)發(fā)web應(yīng)用纫事。Spring MVC是Spring的一個(gè)模塊勘畔,式一個(gè)web框架迷殿。

通過(guò)Dispatcher Servlet, ModelAndView 和 View Resolver,開(kāi)發(fā)web應(yīng)用變得很容易咖杂。解決的問(wèn)題領(lǐng)域是網(wǎng)站應(yīng)用程序或者服務(wù)開(kāi)發(fā)——URL路由庆寺、Session、模板引擎诉字、靜態(tài)Web資源等等懦尝。

Spring Boot的功能Spring Boot實(shí)現(xiàn)了自動(dòng)配置,降低了項(xiàng)目搭建的復(fù)雜度壤圃。

眾所周知Spring框架需要進(jìn)行大量的配置陵霉,Spring Boot引入自動(dòng)配置的概念,讓項(xiàng)目設(shè)置變得很容易伍绳。

Spring Boot本身并不提供Spring框架的核心特性以及擴(kuò)展功能踊挠,只是用于快速、敏捷地開(kāi)發(fā)新一代基于Spring框架的應(yīng)用程序冲杀。也就是說(shuō)效床,它并不是用來(lái)替代Spring的解決方案,而是和Spring框架緊密結(jié)合用于提升Spring開(kāi)發(fā)者體驗(yàn)的工具权谁。

同時(shí)它集成了大量常用的第三方庫(kù)配置(例如Jackson, JDBC, Mongo, Redis, Mail等等)剩檀,Spring Boot應(yīng)用中這些第三方庫(kù)幾乎可以零配置的開(kāi)箱即用(out-of-the-box),大部分的Spring Boot應(yīng)用都只需要非常少量的配置代碼旺芽,開(kāi)發(fā)者能夠更加專注于業(yè)務(wù)邏輯沪猴。

Spring Boot只是承載者,輔助你簡(jiǎn)化項(xiàng)目搭建過(guò)程的采章。如果承載的是WEB項(xiàng)目运嗜,使用Spring MVC作為MVC框架,那么工作流程和你上面描述的是完全一樣的悯舟,因?yàn)檫@部分工作是Spring MVC做的而不是Spring Boot担租。對(duì)使用者來(lái)說(shuō),換用Spring Boot以后图谷,項(xiàng)目初始化方法變了翩活,配置文件變了,另外就是不需要單獨(dú)安裝Tomcat這類容器服務(wù)器了便贵,maven打出jar包直接跑起來(lái)就是個(gè)網(wǎng)站菠镇,但你最核心的業(yè)務(wù)邏輯實(shí)現(xiàn)與業(yè)務(wù)流程實(shí)現(xiàn)沒(méi)有任何變化。

所以承璃,用最簡(jiǎn)練的語(yǔ)言概括就是:

Spring 是一個(gè)“引擎”利耍;

Spring MVC 是基于Spring的一個(gè) MVC 框架 ;

Spring Boot 是基于Spring4的條件注冊(cè)的一套快速開(kāi)發(fā)整合包。

Spring MVC自動(dòng)配置

Spring Boot為Spring MVC提供的auto-configuration適用于大多數(shù)應(yīng)用隘梨,并在Spring默認(rèn)功能上添加了以下特性:

  1. 引入ContentNegotiatingViewResolver和BeanNameViewResolver beans程癌。
  2. 對(duì)靜態(tài)資源的支持,包括對(duì)WebJars的支持轴猎。
  3. 自動(dòng)注冊(cè)Converter嵌莉,GenericConverter,F(xiàn)ormatter beans捻脖。
  4. 對(duì)HttpMessageConverters的支持锐峭。
  5. 自動(dòng)注冊(cè)MessageCodeResolver。
  6. 對(duì)靜態(tài)index.html的支持可婶。
  7. 對(duì)自定義Favicon的支持沿癞。
  8. 自動(dòng)使用ConfigurableWebBindingInitializer bean。

如果保留Spring Boot MVC特性矛渴,你只需添加其他的MVC配置(攔截器椎扬,格式化處理器,視圖控制器等)具温。你可以添加自己的WebMvcConfigurerAdapter類型的@Configuration類蚕涤,而不需要注解@EnableWebMvc。如果希望使用自定義的RequestMappingHandlerMapping桂躏,RequestMappingHandlerAdapter钻趋,或ExceptionHandlerExceptionResolver,你可以聲明一個(gè)WebMvcRegistrationsAdapter實(shí)例提供這些組件剂习。

如果想全面控制Spring MVC,你可以添加自己的@Configuration较沪,并使用@EnableWebMvc注解鳞绕。

HttpMessageConverters

Spring MVC使用HttpMessageConverter接口轉(zhuǎn)換HTTP請(qǐng)求和響應(yīng),合適的默認(rèn)配置可以開(kāi)箱即用尸曼,例如對(duì)象自動(dòng)轉(zhuǎn)換為JSON(使用Jackson庫(kù))或XML(如果Jackson XML擴(kuò)展可用们何,否則使用JAXB),字符串默認(rèn)使用UTF-8編碼控轿。

可以使用Spring Boot的HttpMessageConverters類添加或自定義轉(zhuǎn)換類:

import org.springframework.boot.autoconfigure.web.HttpMessageConverters;
import org.springframework.context.annotation.*;
import org.springframework.http.converter.*;
@Configuration 
public class MyConfiguration {
    @Bean 
     public HttpMessageConverters customConverters() {
        HttpMessageConverter<?> additional = ... 
         HttpMessageConverter<?> another = ... 
         return new HttpMessageConverters(additional, another);
    }
}

上下文中出現(xiàn)的所有HttpMessageConverter bean都將添加到converters列表冤竹,你可以通過(guò)這種方式覆蓋默認(rèn)的轉(zhuǎn)換器列表(converters)。

自定義JSON序列化器和反序列化器

如果使用Jackson序列化茬射,反序列化JSON數(shù)據(jù)鹦蠕,你可能想編寫(xiě)自己的JsonSerializer和JsonDeserializer類。自定義序列化器(serializers)通常通過(guò)Module注冊(cè)到Jackson在抛,但Spring Boot提供了@JsonComponent注解這一替代方式钟病,它能輕松的將序列化器注冊(cè)為Spring Beans。

MessageCodesResolver

Spring MVC有一個(gè)實(shí)現(xiàn)策略,用于從綁定的errors產(chǎn)生用來(lái)渲染錯(cuò)誤信息的錯(cuò)誤碼:MessageCodesResolver肠阱。Spring Boot會(huì)自動(dòng)為你創(chuàng)建該實(shí)現(xiàn)票唆,只要設(shè)置spring.mvc.message-codes-resolver.format屬性為PREFIX_ERROR_CODE或POSTFIX_ERROR_CODE(具體查看DefaultMessageCodesResolver.Format枚舉值)。

靜態(tài)內(nèi)容

默認(rèn)情況下屹徘,Spring Boot從classpath下的/static(/public走趋,/resources或/META-INF/resources)文件夾,或從ServletContext根目錄提供靜態(tài)內(nèi)容噪伊。這是通過(guò)Spring MVC的ResourceHttpRequestHandler實(shí)現(xiàn)的簿煌,你可以自定義WebMvcConfigurerAdapter并覆寫(xiě)addResourceHandlers方法來(lái)改變?cè)撔袨椋虞d靜態(tài)文件)。

在單機(jī)web應(yīng)用中酥宴,容器會(huì)啟動(dòng)默認(rèn)的servlet啦吧,并用它加載ServletContext根目錄下的內(nèi)容以響應(yīng)那些Spring不處理的請(qǐng)求。大多數(shù)情況下這都不會(huì)發(fā)生(除非你修改默認(rèn)的MVC配置)拙寡,因?yàn)镾pring總能夠通過(guò)DispatcherServlet處理這些請(qǐng)求授滓。

你可以設(shè)置spring.resources.staticLocations屬性自定義靜態(tài)資源的位置(配置一系列目錄位置代替默認(rèn)的值),如果你這樣做肆糕,默認(rèn)的歡迎頁(yè)面將從自定義位置加載般堆,所以只要這些路徑中的任何地方有一個(gè)index.html,它都會(huì)成為應(yīng)用的主頁(yè)诚啃。

此外淮摔,除了上述標(biāo)準(zhǔn)的靜態(tài)資源位置,有個(gè)例外情況是Webjars內(nèi)容始赎。任何在/webjars/**路徑下的資源都將從jar文件中提供和橙,只要它們以Webjars的格式打包。

注 如果你的應(yīng)用將被打包成jar造垛,那就不要使用src/main/webapp文件夾魔招。盡管該文件夾是通常的標(biāo)準(zhǔn)格式,但它僅在打包成war的情況下起作用五辽,在打包成jar時(shí)办斑,多數(shù)構(gòu)建工具都會(huì)默認(rèn)忽略它。

Spring Boot也支持Spring MVC提供的高級(jí)資源處理特性杆逗,可用于清除緩存的靜態(tài)資源或?qū)ebJar使用版本無(wú)感知的URLs乡翅。

如果想使用針對(duì)WebJars版本無(wú)感知的URLs(version agnostic),只需要添加webjars-locator依賴罪郊,然后聲明你的Webjar蠕蚜。以jQuery為例,"/webjars/jquery/dist/jquery.min.js"實(shí)際為"/webjars/jquery/x.y.z/dist/jquery.min.js"排龄,x.y.z為Webjar的版本波势。

注 如果使用JBoss翎朱,你需要聲明webjars-locator-jboss-vfs依賴而不是webjars-locator,否則所有的Webjars將解析為404尺铣。

以下的配置為所有的靜態(tài)資源提供一種緩存清除(cache busting)方案拴曲,實(shí)際上是將內(nèi)容hash添加到URLs中,比如<link href="/css/spring-2a2d595e6ed9a0b24f027f2b63b134d6.css"/>:

spring.resources.chain.strategy.content.enabled=true 
spring.resources.chain.strategy.content.paths=/** 

注 實(shí)現(xiàn)該功能的是ResourceUrlEncodingFilter凛忿,它在模板運(yùn)行期會(huì)重寫(xiě)資源鏈接澈灼,Thymeleaf,Velocity和FreeMarker會(huì)自動(dòng)配置該filter店溢,JSP需要手動(dòng)配置叁熔。其他模板引擎還沒(méi)自動(dòng)支持,不過(guò)你可以使用ResourceUrlProvider自定義模塊宏或幫助類床牧。

當(dāng)使用比如JavaScript模塊加載器動(dòng)態(tài)加載資源時(shí)荣回,重命名文件是不行的,這也是提供其他策略并能結(jié)合使用的原因戈咳。下面是一個(gè)"fixed"策略心软,在URL中添加一個(gè)靜態(tài)version字符串而不需要改變文件名:

spring.resources.chain.strategy.content.enabled=true 
spring.resources.chain.strategy.content.paths=/** 
spring.resources.chain.strategy.fixed.enabled=true 
spring.resources.chain.strategy.fixed.paths=/js/lib/ 
spring.resources.chain.strategy.fixed.version=v12 

使用以上策略,JavaScript模塊加載器加載"/js/lib/"下的文件時(shí)會(huì)使用一個(gè)固定的版本策略"/v12/js/lib/mymodule.js"著蛙,其他資源仍舊使用內(nèi)容hash的方式<link href="/css/spring-2a2d595e6ed9a0b24f027f2b63b134d6.css"/>删铃。查看ResourceProperties獲取更多支持的選項(xiàng)。

歡迎頁(yè)面

Spring Boot支持靜態(tài)和模板歡迎頁(yè)面踏堡。它首先index.html在配置的靜態(tài)內(nèi)容位置中查找 文件猎唁。如果找不到,則會(huì)查找index模板顷蟆。如果找到任何一個(gè)诫隅,它將自動(dòng)用作應(yīng)用程序的歡迎頁(yè)面。帐偎、

自定義Favicon

Spring Boot favicon.ico在配置的靜態(tài)內(nèi)容位置和類路徑的根目錄(按此順序)中查找a 阎肝。如果存在這樣的文件,它會(huì)自動(dòng)用作應(yīng)用程序的圖標(biāo)肮街。

路徑匹配和內(nèi)容協(xié)商

Spring MVC可以通過(guò)查看請(qǐng)求路徑并將它匹配到應(yīng)用程序中定義的映射(例如@GetMapping Controller方法上的注釋),將傳入的HTTP請(qǐng)求映射到處理程序判导。

Spring Boot選擇默認(rèn)禁用后綴模式匹配嫉父,這意味著請(qǐng)求"GET /projects/spring-boot.json"不會(huì)匹配 @GetMapping("/projects/spring-boot")映射。這被認(rèn)為是Spring MVC應(yīng)用程序的 最佳實(shí)踐眼刃。此功能在過(guò)去對(duì)于沒(méi)有發(fā)送正確的“Accept”請(qǐng)求標(biāo)頭的HTTP客戶端來(lái)說(shuō)非常有用; 我們需要確保將正確的內(nèi)容類型發(fā)送到客戶端绕辖。如今,內(nèi)容協(xié)商更可靠擂红。

還有其他一些方法可以處理不一致地發(fā)送適當(dāng)?shù)摹敖邮堋闭?qǐng)求標(biāo)頭的HTTP客戶端仪际。我們可以使用查詢參數(shù)來(lái)確保類似的請(qǐng)求"GET /projects/spring-boot?format=json" 將映射到@GetMapping("/projects/spring-boot")以下內(nèi)容,而不是使用后綴匹配:

spring.mvc.contentnegotiation.favor-parameter = true 
#我們可以更改參數(shù)名稱,默認(rèn)為“格式”: 
#spring.mvc.contentnegotiation.parameter-name = myparam 
#我們還可以通過(guò)以下方式注冊(cè)其他文件擴(kuò)展名/媒體類型: 
spring.mvc.contentnegotiation.media-types.markdown = text / markdown 

如果您了解注意事項(xiàng)并仍然希望應(yīng)用程序使用后綴模式匹配树碱,則需要進(jìn)行以下配置:

spring.mvc.contentnegotiation.favor-path-extension = true 
#您也可以將該功能限制為已知擴(kuò)展 
#spring.mvc.pathmatch.use-registered-suffix-pattern = true 
#我們還可以通過(guò)以下方式注冊(cè)其他文件擴(kuò)展名/媒體類型: 
#spring.mvc.contentnegotiation.media-types.adoc = text / asciidoc 

ConfigurableWebBindingInitializer

Spring MVC使用WebBindingInitializer為每個(gè)特殊的請(qǐng)求初始化相應(yīng)的WebDataBinder肯适,如果你創(chuàng)建自己的ConfigurableWebBindingInitializer @Bean,Spring Boot會(huì)自動(dòng)配置Spring MVC使用它成榜。

模板引擎

正如REST web服務(wù)框舔,你也可以使用Spring MVC提供動(dòng)態(tài)HTML內(nèi)容。Spring MVC支持各種各樣的模板技術(shù)赎婚,包括Velocity, FreeMarker和JSPs刘绣,很多其他的模板引擎也提供它們自己的Spring MVC集成。

Spring Boot為以下的模板引擎提供自動(dòng)配置支持:

  • FreeMarker
  • Groovy
  • Thymeleaf
  • Velocity(1.4已不再支持)
  • Mustache

注:由于在內(nèi)嵌servlet容器中使用JSPs存在一些已知的限制挣输,所以建議盡量不使用它們纬凤。

使用以上引擎中的任何一種,并采用默認(rèn)配置撩嚼,則模塊會(huì)從src/main/resources/templates自動(dòng)加載停士。

注:IntelliJ IDEA根據(jù)你運(yùn)行應(yīng)用的方式會(huì)對(duì)classpath進(jìn)行不同的排序。在IDE里通過(guò)main方法運(yùn)行應(yīng)用绢馍,跟從Maven向瓷,或Gradle,或打包好的jar中運(yùn)行相比會(huì)導(dǎo)致不同的順序舰涌,這可能導(dǎo)致Spring Boot不能從classpath下成功地找到模板猖任。如果遇到這個(gè)問(wèn)題,你可以在IDE里重新對(duì)classpath進(jìn)行排序瓷耙,將模塊的類和資源放到第一位朱躺。或者搁痛,你可以配置模塊的前綴為classpath*:/templates/长搀,這樣會(huì)查找classpath下的所有模板目錄。

錯(cuò)誤處理

Spring Boot默認(rèn)提供一個(gè)/error映射用來(lái)以合適的方式處理所有的錯(cuò)誤鸡典,并將它注冊(cè)為servlet容器中全局的 錯(cuò)誤頁(yè)面源请。對(duì)于機(jī)器客戶端(相對(duì)于瀏覽器而言,瀏覽器偏重于人的行為)彻况,它會(huì)產(chǎn)生一個(gè)具有詳細(xì)錯(cuò)誤谁尸,HTTP狀態(tài),異常信息的JSON響應(yīng)纽甘。對(duì)于瀏覽器客戶端良蛮,它會(huì)產(chǎn)生一個(gè)白色標(biāo)簽樣式(whitelabel)的錯(cuò)誤視圖,該視圖將以HTML格式顯示同樣的數(shù)據(jù)(可以添加一個(gè)解析為'error'的View來(lái)自定義它)悍赢。

為了完全替換默認(rèn)的行為决瞳,你可以實(shí)現(xiàn)ErrorController货徙,并注冊(cè)一個(gè)該類型的bean定義,或簡(jiǎn)單地添加一個(gè)ErrorAttributes類型的bean以使用現(xiàn)存的機(jī)制皮胡,只是替換顯示的內(nèi)容痴颊。

注BasicErrorController可以作為自定義ErrorController的基類,如果你想添加對(duì)新context type的處理(默認(rèn)處理text/html)胸囱,這會(huì)很有幫助祷舀。你只需要繼承BasicErrorController,添加一個(gè)public方法烹笔,并注解帶有produces屬性的@RequestMapping裳扯,然后創(chuàng)建該新類型的bean。

你也可以定義一個(gè)@ControllerAdvice去自定義某個(gè)特殊controller或exception類型的JSON文檔:

@ControllerAdvice(basePackageClasses = FooController.class) 
public class FooControllerAdvice extends ResponseEntityExceptionHandler {
    @ExceptionHandler(YourException.class) 
     @ResponseBody 
     ResponseEntity<?> handleControllerException(HttpServletRequest request, Throwable ex) {
        HttpStatus status = getStatus(request);
        return new ResponseEntity<>(new CustomErrorType(status.value(), ex.getMessage()), status);
    }
    private HttpStatus getStatus(HttpServletRequest request) {
        Integer statusCode = (Integer) request.getAttribute("javax.servlet.error.status_code");
        if (statusCode == null) {
            return HttpStatus.INTERNAL_SERVER_ERROR;
        }
        return HttpStatus.valueOf(statusCode);
    }
}

在以上示例中谤职,如果跟FooController相同package的某個(gè)controller拋出YourException饰豺,一個(gè)CustomerErrorType類型的POJO的json展示將代替ErrorAttributes展示。

自定義錯(cuò)誤頁(yè)面

如果想為某個(gè)給定的狀態(tài)碼展示一個(gè)自定義的HTML錯(cuò)誤頁(yè)面允蜈,你需要將文件添加到/error文件夾下冤吨。錯(cuò)誤頁(yè)面既可以是靜態(tài)HTML(比如,任何靜態(tài)資源文件夾下添加的)饶套,也可以是使用模板構(gòu)建的漩蟆,文件名必須是明確的狀態(tài)碼或一系列標(biāo)簽。

例如妓蛮,映射404到一個(gè)靜態(tài)HTML文件怠李,你的目錄結(jié)構(gòu)可能如下:

src/ 
 +- main/ 
 +- java/ 
 | + <source code> 
 +- resources/ 
 +- public/ 
 +- error/ 
 | +- 404.html 
 +- <other public assets> 

使用FreeMarker模板映射所有5xx錯(cuò)誤,你需要如下的目錄結(jié)構(gòu):

src/ 
 +- main/ 
 +- java/ 
 | + <source code> 
 +- resources/ 
 +- templates/ 
 +- error/ 
 | +- 5xx.ftl 
 +- <other templates> 

對(duì)于更復(fù)雜的映射蛤克,你可以添加實(shí)現(xiàn)ErrorViewResolver接口的beans:

public class MyErrorViewResolver implements ErrorViewResolver {
    @Override 
     public ModelAndView resolveErrorView(HttpServletRequest request, 
     HttpStatus status, Map<String, Object> model) {
        // Use the request or status to optionally return a ModelAndView 
        return ...
    }
}

你也可以使用Spring MVC特性捺癞,比如@ExceptionHandler方法和@ControllerAdvice,ErrorController將處理所有未處理的異常构挤。

映射Spring MVC以外的錯(cuò)誤頁(yè)面

對(duì)于不使用Spring MVC的應(yīng)用髓介,你可以通過(guò)ErrorPageRegistrar接口直接注冊(cè)ErrorPages。該抽象直接工作于底層內(nèi)嵌servlet容器筋现,即使你沒(méi)有Spring MVC的DispatcherServlet唐础,它們?nèi)耘f可以工作。

@Bean 
public ErrorPageRegistrar errorPageRegistrar(){
    return new MyErrorPageRegistrar();
}
// ... 
private static class MyErrorPageRegistrar implements ErrorPageRegistrar {
    @Override 
     public void registerErrorPages(ErrorPageRegistry registry) {
        registry.addErrorPages(new ErrorPage(HttpStatus.BAD_REQUEST, "/400"));
    }
}

注.如果你注冊(cè)一個(gè)ErrorPage矾飞,該頁(yè)面需要被一個(gè)Filter處理(在一些非Spring web框架中很常見(jiàn)彻犁,比如Jersey,Wicket)凰慈,那么該Filter需要明確注冊(cè)為一個(gè)ERROR分發(fā)器(dispatcher),例如:

@Bean 
public FilterRegistrationBean myFilter() {
    FilterRegistrationBean registration = new FilterRegistrationBean();
    registration.setFilter(new MyFilter());
    ... 
     registration.setDispatcherTypes(EnumSet.allOf(DispatcherType.class));
    return registration;
}

(默認(rèn)的FilterRegistrationBean不包含ERROR dispatcher類型)驼鹅。

WebSphere應(yīng)用服務(wù)器的錯(cuò)誤處理

當(dāng)部署到一個(gè)servlet容器時(shí)微谓,Spring Boot通過(guò)它的錯(cuò)誤頁(yè)面過(guò)濾器將帶有錯(cuò)誤狀態(tài)的請(qǐng)求轉(zhuǎn)發(fā)到恰當(dāng)?shù)腻e(cuò)誤頁(yè)面森篷。request只有在response還沒(méi)提交時(shí)才能轉(zhuǎn)發(fā)(forwarded)到正確的錯(cuò)誤頁(yè)面,而WebSphere應(yīng)用服務(wù)器8.0及后續(xù)版本默認(rèn)情況會(huì)在servlet方法成功執(zhí)行后提交response豺型,你需要設(shè)置com.ibm.ws.webcontainer.invokeFlushAfterService屬性為false來(lái)關(guān)閉該行為仲智。

Spring HATEOAS

如果正在開(kāi)發(fā)基于超媒體的RESTful API,你可能需要Spring HATEOAS姻氨,而Spring Boot會(huì)為其提供自動(dòng)配置钓辆,這在大多數(shù)應(yīng)用中都運(yùn)作良好。 自動(dòng)配置取代了@EnableHypermediaSupport肴焊,只需注冊(cè)一定數(shù)量的beans就能輕松構(gòu)建基于超媒體的應(yīng)用前联,這些beans包括LinkDiscoverers(客戶端支持),ObjectMapper(用于將響應(yīng)編排為想要的形式)娶眷。ObjectMapper可以根據(jù)spring.jackson.*屬性或Jackson2ObjectMapperBuilder bean進(jìn)行自定義似嗤。

通過(guò)注解@EnableHypermediaSupport,你可以控制Spring HATEOAS的配置届宠,但這會(huì)禁用上述ObjectMapper的自定義功能烁落。

CORS支持

跨域資源共享(CORS)是一個(gè)大多數(shù)瀏覽器都實(shí)現(xiàn)了的W3C標(biāo)準(zhǔn),它允許你以靈活的方式指定跨域請(qǐng)求如何被授權(quán)豌注,而不是采用那些不安全伤塌,性能低的方式,比如IFRAME或JSONP轧铁。

從4.2版本開(kāi)始每聪,Spring MVC對(duì)CORS提供開(kāi)箱即用的支持。不用添加任何特殊配置属桦,只需要在Spring Boot應(yīng)用的controller方法上注解@CrossOrigin熊痴,并添加CORS配置。通過(guò)注冊(cè)一個(gè)自定義addCorsMappings(CorsRegistry)方法的WebMvcConfigurer bean可以指定全局CORS配置:

@Configuration 
public class MyConfiguration {
    @Bean 
     public WebMvcConfigurer corsConfigurer() {
        return new WebMvcConfigurerAdapter() {
            @Override 
             public void addCorsMappings(CorsRegistry registry) {
                registry.addMapping("/api/**");
            }
        }
        ;
    }
}
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請(qǐng)聯(lián)系作者
  • 序言:七十年代末聂宾,一起剝皮案震驚了整個(gè)濱河市果善,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌系谐,老刑警劉巖巾陕,帶你破解...
    沈念sama閱讀 218,546評(píng)論 6 507
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場(chǎng)離奇詭異纪他,居然都是意外死亡鄙煤,警方通過(guò)查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,224評(píng)論 3 395
  • 文/潘曉璐 我一進(jìn)店門(mén)茶袒,熙熙樓的掌柜王于貴愁眉苦臉地迎上來(lái)梯刚,“玉大人,你說(shuō)我怎么就攤上這事薪寓⊥鲎剩” “怎么了澜共?”我有些...
    開(kāi)封第一講書(shū)人閱讀 164,911評(píng)論 0 354
  • 文/不壞的土叔 我叫張陵,是天一觀的道長(zhǎng)锥腻。 經(jīng)常有香客問(wèn)我嗦董,道長(zhǎng),這世上最難降的妖魔是什么瘦黑? 我笑而不...
    開(kāi)封第一講書(shū)人閱讀 58,737評(píng)論 1 294
  • 正文 為了忘掉前任京革,我火速辦了婚禮,結(jié)果婚禮上幸斥,老公的妹妹穿的比我還像新娘匹摇。我一直安慰自己,他們只是感情好睡毒,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,753評(píng)論 6 392
  • 文/花漫 我一把揭開(kāi)白布来惧。 她就那樣靜靜地躺著,像睡著了一般演顾。 火紅的嫁衣襯著肌膚如雪供搀。 梳的紋絲不亂的頭發(fā)上,一...
    開(kāi)封第一講書(shū)人閱讀 51,598評(píng)論 1 305
  • 那天钠至,我揣著相機(jī)與錄音葛虐,去河邊找鬼。 笑死棉钧,一個(gè)胖子當(dāng)著我的面吹牛屿脐,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播宪卿,決...
    沈念sama閱讀 40,338評(píng)論 3 418
  • 文/蒼蘭香墨 我猛地睜開(kāi)眼的诵,長(zhǎng)吁一口氣:“原來(lái)是場(chǎng)噩夢(mèng)啊……” “哼!你這毒婦竟也來(lái)了佑钾?” 一聲冷哼從身側(cè)響起西疤,我...
    開(kāi)封第一講書(shū)人閱讀 39,249評(píng)論 0 276
  • 序言:老撾萬(wàn)榮一對(duì)情侶失蹤,失蹤者是張志新(化名)和其女友劉穎休溶,沒(méi)想到半個(gè)月后代赁,有當(dāng)?shù)厝嗽跇?shù)林里發(fā)現(xiàn)了一具尸體,經(jīng)...
    沈念sama閱讀 45,696評(píng)論 1 314
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡兽掰,尸身上長(zhǎng)有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,888評(píng)論 3 336
  • 正文 我和宋清朗相戀三年芭碍,在試婚紗的時(shí)候發(fā)現(xiàn)自己被綠了。 大學(xué)時(shí)的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片孽尽。...
    茶點(diǎn)故事閱讀 40,013評(píng)論 1 348
  • 序言:一個(gè)原本活蹦亂跳的男人離奇死亡窖壕,死狀恐怖,靈堂內(nèi)的尸體忽然破棺而出,到底是詐尸還是另有隱情艇拍,我是刑警寧澤狐蜕,帶...
    沈念sama閱讀 35,731評(píng)論 5 346
  • 正文 年R本政府宣布,位于F島的核電站卸夕,受9級(jí)特大地震影響,放射性物質(zhì)發(fā)生泄漏婆瓜。R本人自食惡果不足惜快集,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,348評(píng)論 3 330
  • 文/蒙蒙 一、第九天 我趴在偏房一處隱蔽的房頂上張望廉白。 院中可真熱鬧个初,春花似錦、人聲如沸猴蹂。這莊子的主人今日做“春日...
    開(kāi)封第一講書(shū)人閱讀 31,929評(píng)論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽(yáng)磅轻。三九已至珍逸,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間聋溜,已是汗流浹背谆膳。 一陣腳步聲響...
    開(kāi)封第一講書(shū)人閱讀 33,048評(píng)論 1 270
  • 我被黑心中介騙來(lái)泰國(guó)打工, 沒(méi)想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留撮躁,地道東北人漱病。 一個(gè)月前我還...
    沈念sama閱讀 48,203評(píng)論 3 370
  • 正文 我出身青樓,卻偏偏與公主長(zhǎng)得像把曼,于是被迫代替她去往敵國(guó)和親杨帽。 傳聞我的和親對(duì)象是個(gè)殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 44,960評(píng)論 2 355

推薦閱讀更多精彩內(nèi)容

  • spring boot就是一個(gè)大框架里面包含了許許多多的東西嗤军,其中spring就是最核心的內(nèi)容之一注盈,當(dāng)然就包含sp...
    架構(gòu)師springboot閱讀 469評(píng)論 0 1
  • SpringMVC原理分析 Spring Boot學(xué)習(xí) 5、Hello World探究 1型雳、POM文件 1当凡、父項(xiàng)目...
    jack_jerry閱讀 1,296評(píng)論 0 1
  • 我有一個(gè)同事特別喜歡抱怨,直言說(shuō)她進(jìn)公司沒(méi)多久就不是很喜歡她纠俭,她進(jìn)入公司沒(méi)幾天自從熟悉了公司和人之后就開(kāi)始各種抱怨...
    小貍拆書(shū)講知識(shí)閱讀 250評(píng)論 0 0
  • 岳把視頻發(fā)給我的時(shí)候沿量,我把這一天的疲憊都笑沒(méi)了,他說(shuō)冤荆,我還有照片朴则,合照,你站在最后排钓简,不看鏡頭乌妒,那時(shí)候窗外有什么吸...
    大寨閱讀 216評(píng)論 1 1
  • 我不想長(zhǎng)大 長(zhǎng)大了就不能 和小朋友們快樂(lè)的玩游戲 和小花小草愉快的談世界 所以 我永遠(yuǎn)不想長(zhǎng)大汹想!
    小果子1002閱讀 96評(píng)論 0 2