Настройка весеннего запуска приложения с помощью web.xml
Я обновляю существующее веб-приложение Spring, чтобы сгенерированный файл war включал веб-сервер Jetty. Я хочу максимально использовать существующую конфигурацию, чтобы ограничить регрессии.
Вот существующий web.xml
:
<web-app id="fbecart-webapp" version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
<context-param>
<param-name>contextClass</param-name>
<param-value>org.springframework.web.context.support.AnnotationConfigWebApplicationContext</param-value>
</context-param>
<context-param>
<param-name>contextConfigLocation</param-name>
<param-value>com.fbecart.ApplicationConfiguration</param-value>
</context-param>
<listener>
<listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
</listener>
<servlet>
<servlet-name>spring-dispatcher</servlet-name>
<servlet-class>com.fbecart.MyDispatcherServlet</servlet-class>
<init-param>
<param-name>dispatchOptionsRequest</param-name>
<param-value>true</param-value>
</init-param>
<init-param>
<param-name>contextClass</param-name>
<param-value>org.springframework.web.context.support.AnnotationConfigWebApplicationContext</param-value>
</init-param>
<init-param>
<param-name>contextConfigLocation</param-name>
<param-value>com.fbecart.SpringDispatcherServletConfiguration</param-value>
</init-param>
<load-on-startup>1</load-on-startup>
</servlet>
<servlet-mapping>
<servlet-name>spring-dispatcher</servlet-name>
<url-pattern>/*</url-pattern>
</servlet-mapping>
<filter>
<filter-name>GzipFilter</filter-name>
<filter-class>org.eclipse.jetty.servlets.GzipFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>GzipFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<filter>
<filter-name>encodingFilter</filter-name>
<filter-class>org.springframework.web.filter.CharacterEncodingFilter</filter-class>
<init-param>
<param-name>encoding</param-name>
<param-value>UTF-8</param-value>
</init-param>
<init-param>
<param-name>forceEncoding</param-name>
<param-value>true</param-value>
</init-param>
</filter>
<filter-mapping>
<filter-name>encodingFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
<filter>
<filter-name>openSessionInView</filter-name>
<filter-class>org.springframework.orm.jpa.support.OpenEntityManagerInViewFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>openSessionInView</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
</web-app>
Вот мой основной класс JettyApplication.java
:
package com.fbecart;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.web.EmbeddedServletContainerAutoConfiguration;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;
@Configuration
@Import({ ApplicationConfiguration.class, SpringDispatcherServletConfiguration.class,
EmbeddedServletContainerAutoConfiguration.class })
public class JettyApplication {
public static void main(String[] args) throws Exception {
SpringApplication.run(JettyApplication.class, args);
}
}
Я сделал несколько изменений в моих скриптах сборки Gradle, чтобы он заработал:
- добавление зависимостей к spring-boot-starter и spring-boot-starter-jetty
- конфигурация плагина пружинной загрузки
Приложение запускается нормально, контроллеры загружены, и я могу запросить сервер. Но ни один из фильтров, определенных в web.xml, не включен.
Теперь я хотел бы удалить импорт PropertiesConfiguration.class
, ApplicationConfiguration.class
а также SpringDispatcherServletConfiguration.class
в JettyApplication.java
и каким-то образом заменить их путем загрузки или импорта содержимого web.xml
во встроенный контейнер сервлетов. Но я игнорирую, если это правильная стратегия, и если я могу сделать это. Я был бы очень признателен за любую помощь.
-- РЕШЕНИЕ
Вот финал JettyApplication.class
основываясь на ответе Дэйва:
package com.fbecart;
import org.eclipse.jetty.servlets.GzipFilter;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.web.EmbeddedServletContainerAutoConfiguration;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.Import;
import org.springframework.orm.jpa.support.OpenEntityManagerInViewFilter;
import org.springframework.web.filter.CharacterEncodingFilter;
import org.springframework.web.servlet.DispatcherServlet;
@Configuration
@Import({ ApplicationConfiguration.class, SpringDispatcherServletConfiguration.class,
EmbeddedServletContainerAutoConfiguration.class })
public class JettyApplication {
public static void main(String[] args) throws Exception {
SpringApplication.run(JettyApplication.class, args);
}
@Bean
public DispatcherServlet dispatcherServlet() {
return new MyDispatcherServlet();
}
@Bean
public GzipFilter gzipFilter() {
return new GzipFilter();
}
@Bean
public CharacterEncodingFilter characterEncodingFilter() {
final CharacterEncodingFilter characterEncodingFilter = new CharacterEncodingFilter();
characterEncodingFilter.setEncoding("UTF-8");
characterEncodingFilter.setForceEncoding(true);
return characterEncodingFilter;
}
@Bean
public OpenEntityManagerInViewFilter openEntityManagerInViewFilter() {
return new OpenEntityManagerInViewFilter();
}
}
Я заменю web.xml на ServletContainerInitializer в ближайшем будущем... следите за обновлениями;)
1 ответ
На вашем месте я бы медленно попытался очистить слои в файле web.xml и полностью удалить их. Таким образом, у вас будет только одна конфигурация для всего приложения, включая все фильтры и сервлеты (это идея в любом случае). Вы можете выполнять параллельный запуск, пока вы стабилизируете, где фильтры дублируются в web.xml, и затем, когда у вас есть те же функции в основном приложении, вы можете просто удалить web.xml. Чтобы добавить фильтры в основное приложение, просто создайте определения @Bean для Filter
или же FilterRegistrationBean
экземпляров.
Вы всегда можете поддержать развертывание войны через SpringBootServletInitializer
а также при необходимости.