深入Spring Boot實(shí)現(xiàn)對Fat Jar jsp的支持
spring boot 對于jsp支持的限制
對于jsp的支持,Spring Boot官方只支持了war的打包方式,不支持fat jar。參考官方文檔: https://docs.spring.io/spring-boot/docs/current/reference/html/boot-features-developing-web-applications.html#boot-features-jsp-limitations
這里spring boot官方說是tomcat的問題,實(shí)際上是spring boot自己改變了打包格式引起的。參考之前的文章:http://www.dhdzp.com/article/141479.htm
原來的結(jié)構(gòu)之下,tomcat是可以掃描到fat jar里的META-INF/resources目錄下面的資源的。在增加了BOOT-INF/classes之后,則tomcat掃描不到了。
那么怎么解決這個(gè)問題呢?下面給出一種方案,來實(shí)現(xiàn)對spring boot fat jar/exploded directory的jsp的支持。
個(gè)性化配置tomcat,把BOOT-INF/classes 加入tomcat的ResourceSet
在tomcat里,所有掃描到的資源都會放到所謂的ResourceSet里。比如servlet 3規(guī)范里的應(yīng)用jar包的META-INF/resources就是一個(gè)ResourceSet。
現(xiàn)在需要想辦法把spring boot打出來的fat jar的BOOT-INF/classes目錄加到ResourceSet里。
下面通過實(shí)現(xiàn)tomcat的 LifecycleListener接口,在Lifecycle.CONFIGURE_START_EVENT事件里,獲取到BOOT-INF/classes的URL,再把這個(gè)URL加入到WebResourceSet里。
/**
* Add main class fat jar/exploded directory into tomcat ResourceSet.
*
* @author hengyunabc 2017-07-29
*
*/
public class StaticResourceConfigurer implements LifecycleListener {
private final Context context;
StaticResourceConfigurer(Context context) {
this.context = context;
}
@Override
public void lifecycleEvent(LifecycleEvent event) {
if (event.getType().equals(Lifecycle.CONFIGURE_START_EVENT)) {
URL location = this.getClass().getProtectionDomain().getCodeSource().getLocation();
if (ResourceUtils.isFileURL(location)) {
// when run as exploded directory
String rootFile = location.getFile();
if (rootFile.endsWith("/BOOT-INF/classes/")) {
rootFile = rootFile.substring(0, rootFile.length() - "/BOOT-INF/classes/".length() + 1);
}
if (!new File(rootFile, "META-INF" + File.separator + "resources").isDirectory()) {
return;
}
try {
location = new File(rootFile).toURI().toURL();
} catch (MalformedURLException e) {
throw new IllegalStateException("Can not add tomcat resources", e);
}
}
String locationStr = location.toString();
if (locationStr.endsWith("/BOOT-INF/classes!/")) {
// when run as fat jar
locationStr = locationStr.substring(0, locationStr.length() - "/BOOT-INF/classes!/".length() + 1);
try {
location = new URL(locationStr);
} catch (MalformedURLException e) {
throw new IllegalStateException("Can not add tomcat resources", e);
}
}
this.context.getResources().createWebResourceSet(ResourceSetType.RESOURCE_JAR, "/", location,
"/META-INF/resources");
}
}
}
為了讓spring boot embedded tomcat加載這個(gè) StaticResourceConfigurer,還需要一個(gè)EmbeddedServletContainerCustomizer的配置:
@Configuration
@ConditionalOnProperty(name = "tomcat.staticResourceCustomizer.enabled", matchIfMissing = true)
public class TomcatConfiguration {
@Bean
public EmbeddedServletContainerCustomizer staticResourceCustomizer() {
return new EmbeddedServletContainerCustomizer() {
@Override
public void customize(ConfigurableEmbeddedServletContainer container) {
if (container instanceof TomcatEmbeddedServletContainerFactory) {
((TomcatEmbeddedServletContainerFactory) container)
.addContextCustomizers(new TomcatContextCustomizer() {
@Override
public void customize(Context context) {
context.addLifecycleListener(new StaticResourceConfigurer(context));
}
});
}
}
};
}
}
這樣子的話,spring boot就可以支持fat jar里的jsp資源了。
demo地址: https://github.com/hengyunabc/spring-boot-fat-jar-jsp-sample
總結(jié)
- spring boot改變了打包結(jié)構(gòu),導(dǎo)致tomcat沒有辦法掃描到fat jar里的/
BOOT-INF/classes - 通過一個(gè)
StaticResourceConfigurer把fat jar里的/BOOT-INF/classes加到tomcat的ResourceSet來解決問題
以上就是本文的全部內(nèi)容,希望對大家的學(xué)習(xí)有所幫助,也希望大家多多支持腳本之家。
相關(guān)文章
解讀@ConfigurationProperties的基本用法
這篇文章主要介紹了@ConfigurationProperties的基本用法,具有很好的參考價(jià)值,希望對大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2025-03-03
Java中十進(jìn)制和十六進(jìn)制的相互轉(zhuǎn)換方法
下面小編就為大家?guī)硪黄狫ava中十進(jìn)制和十六進(jìn)制的相互轉(zhuǎn)換方法。小編覺得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過來看看吧2016-08-08
Java利用Socket類實(shí)現(xiàn)TCP通信程序
TCP通信能實(shí)現(xiàn)兩臺計(jì)算機(jī)之間的數(shù)據(jù)交互,通信的兩端,要嚴(yán)格區(qū)分為客戶端與服務(wù)端,下面我們就來看看Java如何利用Socket類實(shí)現(xiàn)TCP通信程序吧2024-02-02
java按照模板導(dǎo)出pdf或word文件詳細(xì)代碼
有時(shí)候業(yè)務(wù)中我們需要使用pdf模板生成一份pdf文件,下面這篇文章主要給大家介紹了關(guān)于java按照模板導(dǎo)出pdf或word文件的相關(guān)資料,文中給出了詳細(xì)的代碼示例,需要的朋友可以參考下2023-11-11
Springboot中spring-boot-starter-quartz的使用及說明
這篇文章主要介紹了Springboot中spring-boot-starter-quartz的使用及說明,具有很好的參考價(jià)值,希望對大家有所幫助。如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2022-12-12

