配置端口、项目路径
SpringBoot默认采用嵌入式的Servlet容器(Tomcat)。
那么内嵌的Servlet配置如何修改?
- 可以使用配置文件或者yml文件来修改
server:
port: 80
content-path: /crud
tomcat:
uri-encoding: UTF-8
#通用Servlet容器配置
server.xxx
#Tomcat配置
server.tomcat.xxx
- 编写WebServerFactoryCustomizer (自定义Web服务工厂)来修改Servlet容器配置
由于继承WebMvcConfigurationSupport使自动化配置失效BeanCreationException、BeanInstantiationException
@Configuration
public class MyMvcConfig implements WebMvcConfigurer {
// Spring Boot2.0以上版本EmbeddedServletContainerCustomizer被WebServerFactoryCustomizer替代
@Bean
public WebServerFactoryCustomizer<ConfigurableWebServerFactory> webServerFactoryCustomizer(){
return new WebServerFactoryCustomizer<ConfigurableWebServerFactory>() {
@Override
public void customize(ConfigurableWebServerFactory factory) {
factory.setPort(8081);
}
};
}
}
注册Servlet、Filter、Listener
ServletRegisterationBean
FilterRegisterationBean
ServerListenerRegisterationBean
注册Servlet
- 编写MyServlet
public class MyServlet extends HttpServlet {
@Override
protected void doGet(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
doPost(req, resp);
}
@Override
protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws ServletException, IOException {
resp.getWriter().println("<h1>HELLO MY SERVLET</h1>");
}
}
- 编写MyFilter.java
public class MyFilter implements Filter {
@Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
System.out.println("MyFilter Process...");
chain.doFilter(request,response);
}
@Override
public void init(FilterConfig filterConfig) throws ServletException {
}
@Override
public void destroy() {
}
}
- 编写MyListener.java
public class MyListener implements ServletContextListener {
@Override
public void contextInitialized(ServletContextEvent sce) {
System.out.println("contentInit...web启动。。。");
}
@Override
public void contextDestroyed(ServletContextEvent sce) {
System.out.println("contextDestroy...当前web项目销毁。。。");
}
}
- 编写配置类
@Configuration
public class MyServerConfig {
@Bean
public ServletRegistrationBean myServlet(){
return new ServletRegistrationBean<>(new MyServlet(),"/myServlet");
}
@Bean
public FilterRegistrationBean myFilter(){
FilterRegistrationBean registrationBean = new FilterRegistrationBean();
registrationBean.setFilter(new MyFilter());
registrationBean.addUrlPatterns("/hello","/myServlet");
return registrationBean;
}
@Bean
public ServletListenerRegistrationBean servletListenerRegistrationBean(){
return new ServletListenerRegistrationBean(new MyListener());
}
}
- 启动项目可以看到监听器的消息web启动。访问
http://127.0.0.1/crud/myServlet
可见浏览器回显HELLO MY SERVLET,并可以看到控制台的拦截器输入消息。在编译器点击退出时,正常退出则可以看到web销毁的输出。 - 由于SpringBoot默认以jar包的方式启动SpringBoot的web应用,并没有web.xml文件。可以采用上述方式来注册三大组件。
SpringBoot在自动配置SpringMVC的时候,自动注册了SpringMVC的前端控制器:DispatcherServlet
在 org.springframework.boot.autoconfigure.web.servlet.DispatcherServletAutoConfiguration
中
public DispatcherServletRegistrationBean dispatcherServletRegistration(DispatcherServlet dispatcherServlet, WebMvcProperties webMvcProperties, ObjectProvider<MultipartConfigElement> multipartConfig) {
DispatcherServletRegistrationBean registration = new DispatcherServletRegistrationBean(dispatcherServlet, webMvcProperties.getServlet().getPath());
//在 WebMvcProperties 中配置了默认拦截路径“/”,我们可以通过spring.mvc.servlet.path=/* 来修改。但对于旧版本可以使用server.servlet.path=/*
// “/”表示拦截所有请求,包括静态资源,除了jsp。但/*会拦截jsp
registration.setName("dispatcherServlet");
registration.setLoadOnStartup(webMvcProperties.getServlet().getLoadOnStartup());
multipartConfig.ifAvailable(registration::setMultipartConfig);
return registration;
}
切换其他Servlet容器
Tomcat(默认)、Jetty(长连接应用)、Undertow(不支持JSP,但高性能非阻塞,并发性好)
示例:
- 将tomcat排除,可以点击Exclude
或采用pox.xml编写配置
<!-- web模块 -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<!-- 使用Jetty,需要在spring-boot-starter-web排除spring-boot-starter-tomcat,因为SpringBoot默认使用tomcat -->
<exclusions>
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
</exclusion>
</exclusions>
</dependency>
- 引入依赖
<dependency>
<artifactId>spring-boot-starter-jetty</artifactId>
<groupId>org.springframework.boot</groupId>
</dependency>
- 再次启动,可见启动的容器已经是Jetty了。如果不行的话可以重启编译器重试。
- 修改为undertow后,可见控制台已经以undertow启动
使用外部Servlet容器&JSP支持
嵌入式Servlet容器:
优点:简单,方便
缺点:默认不支持JSP,优化定制复杂(使用定制器[ServerProperties、自定义EmbededServletContainerCustomizer],或自己编写嵌入式Servlet容器的创建工厂)
外置Servlet容器:
外面安装Tomcat—应用以war包的方式打包
步骤:
- 创建一个Spring的war项目
- 将嵌入式的Tomcat指定为provide
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
<scope>provided</scope>
</dependency>
- 必须编写一个
SpringBootServletInitializer
子类,并调用configure方法
public class ServletInitializer extends SpringBootServletInitializer {
@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
//传入SpringBoot应用的主程序
return application.sources(WebjspApplication.class);
}
}
- 启动服务器
示例如下:
- 创建springBoot工程,引入web依赖,并以war包方式打包
- 创建相关文件
- 配置tomcat运行环境
- 编写
index.jsp
页面
<%@ page contentType="text/html;charset=UTF-8" language="java" %>
<html>
<head>
<title>Title</title>
</head>
<body>
<h1>THIS IS JSP PAGE</h1>
<a href="success">SUCCESS</a>
</body>
</html>
- 编写Controller
@Controller
public class HelloController {
@GetMapping("/success")
public String success(){
return "success";
}
}
- 编写配置文件
spring.mvc.view.prefix=/WEB-INF/
spring.mvc.view.suffix=.jsp
-
目录结构
-
运行测试成功显示创建的JSP页面
注意:这里运行的是配置的tomcat,而不是springboot项目。如上图红线处所示!