一、概述
因为项目需要,需要再原先项目中发布或者调用WebService服务,考虑到集成Springboot框架,于是采用CXF框架。
WebService注册服务如下:
1 @Configuration 2 public class CxfWebServiceConfig { 3 4 5 @Autowired 6 private HelloWebService helloWebService; 7 8 @Bean 9 public ServletRegistrationBean dispatcherServlet() { 10 return new ServletRegistrationBean(new CXFServlet(), "/service/*");//发布服务名称 11 } 12 13 @Bean(name = Bus.DEFAULT_BUS_ID) 14 public SpringBus springBus() { 15 return new SpringBus(); 16 } 17 18 public HelloWebService helloWebService(){ 19 return new HelloWebServiceImpl(); 20 } 21 22 @Bean 23 public Endpoint endpoint(){ 24 EndpointImpl endpoint = new EndpointImpl(springBus(),helloWebService); 25 endpoint.publish("/HelloWebService"); 26 return endpoint; 27 } 28 29 }
在将CXF集成之后,WebService服务能够正常访问,但是原先的http服务不能访问
因为springboot程序中默认注册的是 dispatcherServlet,在发不了WebService服务之后,相当于手动配置 ServletRegistrationBean,这时springboot不会再去注册默认的dispatcherServlet,解决办法就是需要我们在启动类里手动去注册一个dispatcherServlet
spring boot中注册Servlet的两种方式
但spring boot把tomcat都给隐藏了,更别说web.xml了。好在提供了另外的方式配置servlet。
1.@WebServlet注解:
这个是javaee的注解,是servlet3.0以后提供的。spring boot会扫描这个注解,并将这个注解注解的类注册到web容器中作为一个servlet。
但是DispatcherServlet并不是自定义的servlet,而是框架提供的servlet,所以此方法不行。
2.ServletRegistrationBean:
这个bean是由spring boot提供专门来注册servlet的,可以象注册bean一样去配置servlet。
1 @Bean 2 public ServletRegistrationBean dispatcherServlet() { 3 //注解扫描上下文 4 AnnotationConfigWebApplicationContext applicationContext = new AnnotationConfigWebApplicationContext(); 5 //项目包名 6 applicationContext.scan("com.surfilter.*"); 7 DispatcherServlet rest_dispatcherServlet = new DispatcherServlet(applicationContext); 8 ServletRegistrationBean registrationBean = new ServletRegistrationBean(rest_dispatcherServlet); 9 registrationBean.setLoadOnStartup(1); 10 registrationBean.addUrlMappings("/*"); 11 //一定要加上此行 12 registrationBean.setName("rest_dispatcherServlet"); 13 return registrationBean; 14 }
如果不指定,默认为“dispatcherServlet”而spring boot提供的DispatcherServlet的name就是“dispatcherServlet”。可以在spring boot的DispatcherServletAutoConfiguration类中找到:
1 public ServletRegistrationBean dispatcherServletRegistration(DispatcherServlet dispatcherServlet) { 2 ServletRegistrationBean registration = new ServletRegistrationBean(dispatcherServlet, new String[]{this.serverProperties.getServletMapping()}); 3 registration.setName("dispatcherServlet"); 4 registration.setLoadOnStartup(this.webMvcProperties.getServlet().getLoadOnStartup()); 5 if(this.multipartConfig != null) { 6 registration.setMultipartConfig(this.multipartConfig); 7 } 8 9 return registration; 10 } 11 }
所以为了不覆盖默认的dispatcherServlet,必须指定一个别的名称
同时,在自定义的DispathcerServlet绑定的配置类上,要配置报扫描的话,必须要加上@EnableWebMvc注解,不然不会扫描@Contrller注解。
1 @RestController 2 @RequestMapping("/api/1.0/hello") 3 @EnableWebMvc 4 public class RestController { 5 ...... 6 }
屏蔽rest服务DispatcherServlet对静态资源的访问
最后还有一个小问题,因为想让额外配置的一个DispatcherServlet专门用于提供rest服务,但是这样配置之后,访问localhost/rest/时会访问到页面等静态资源,感觉怪怪的。
因为spring boot默认是对静态资源做了映射的,但如果不想要访问到任何静态的资源,可以修改这个映射。
两种方式:
1.在application.yml中配置:
1 spring: 2 mvc: 3 #默认为/** 4 static-path-pattern: /** 5 resources: 6 #默认为classpath:/META-INF/resources/,classpath:/resources/,classpath:/static/,classpath:/public/ 。配置多个路径,中间用逗号隔开。 7 static-locations:
2.继承WebMvcConfigurerAdapter的java类中配置:
1 @Configuration 2 @EnableWebMvc 3 public class Cfg_View extends WebMvcConfigurerAdapter{ 4 @Override 5 public void addResourceHandlers(ResourceHandlerRegistry registry) { 6 registry.addResourceHandler("/**"); 7 } 8 }