使用tomcat和cxf-servlet进行spring-boot

时间:2014-06-02 19:45:54

标签: spring tomcat servlets cxf spring-boot

我试图通过spring-boot站起来嵌入Tomcat。我想在应用程序中使用CXF作为一组Web服务,但我无法弄清楚如何站起来使用CXF servlet。

我的主要课程看起来像这样......

@Configuration
@EnableAutoConfiguration
@ComponentScan(basePackages={"com.connecture.services.documentservice.webservice"})
public class Application {

    public static void main(String[] args) {
        SpringApplication.run(new Class[] { Application.class, CfxInitializer.class }, args);
    }

    @Bean
  public EmbeddedServletContainerFactory embeddedServletContainerFactory() {
      TomcatEmbeddedServletContainerFactory factory = new TomcatEmbeddedServletContainerFactory("", 8080);
      return factory;
  }

}

我的CfxInitializer就是这样......

public class CfxInitializer implements ServletContextInitializer
{

  @Override
  public void onStartup(ServletContext servletContext) throws ServletException
  {
    XmlWebApplicationContext rootContext = new XmlWebApplicationContext();  
    rootContext.setConfigLocations(new String[] { "classpath*:applicationContext.xml" });  
    servletContext.addListener(new ContextLoaderListener(rootContext));  

    ServletRegistration.Dynamic dispatcher = servletContext.addServlet("CXFServlet", CXFServlet.class);  
    dispatcher.addMapping("/api/*");  
  }

}

当我尝试使用典型命令./gradlew build && java -jar build/libs/gs-spring-boot-0.1.0.jar

构建和启动jar时

我得到多个上下文的异常。

Java.lang.IllegalStateException: Cannot initialize context because there is already a root application context present - check whether you have multiple ContextLoader* definitions in your web.xml!
    at org.springframework.web.context.ContextLoader.initWebApplicationContext(ContextLoader.java:277)
    at org.springframework.web.context.ContextLoaderListener.contextInitialized(ContextLoaderListener.java:106)
    at org.apache.catalina.core.StandardContext.listenerStart(StandardContext.java:4971)
    at org.apache.catalina.core.StandardContext.startInternal(StandardContext.java:5467)
    at org.apache.catalina.util.LifecycleBase.start(LifecycleBase.java:150)
    at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1559)
    at org.apache.catalina.core.ContainerBase$StartChild.call(ContainerBase.java:1549)
    at java.util.concurrent.FutureTask.run(FutureTask.java:262)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
    at java.lang.Thread.run(Thread.java:745)

这是一个更完整的pastebin - http://pastebin.com/bcJ2ULhM

----------------------------------------------- -----------------------------------

与Dave的答案类似,我可以通过删除ServletContextInitializer并将bean添加到Application Class来修复它。

@Bean
  public ServletRegistrationBean servletRegistrationBean(){
      return new ServletRegistrationBean(new CXFServlet(),"/api/*");
  }

3 个答案:

答案 0 :(得分:6)

Spring Boot嵌入式servlet功能旨在与ServletServletRegistration @Beans一起使用,而不是ContextLoaderListener(看起来它正试图窃取根上下文的ServletContext属性)。尝试为您的servlet添加ServletRegistration;如果它是Spring知道的,假设它有一个允许你更改应用程序上下文或上下文位置的接口,那么你应该能够在注册中配置它。

答案 1 :(得分:3)

我在github上找到了以下项目,这帮助我开始了

https://github.com/ungerts/spring-boot-jaxrs-sample

为我工作:

  • spring-boot 1.2.3
  • CXF-RT-前端-JAXRS:3.1.0
  • 杰克逊 - JAXRS-JSON-提供商:2.5.3

答案 2 :(得分:0)