Apache CXF在关闭tomcat时挂起

时间:2014-07-30 15:00:00

标签: tomcat cxf jax-ws spring-java-config

我将CXFServlet连接到我的应用程序,该应用程序已连接到调度程序servlet。端点工作得很好,一切似乎都工作,直到我们关闭tomcat。我发现我可以连接CXFServlet并且tomcat在没有问题的情况下关闭,直到我接通总线。之后我看到关机挂起的问题。 要关闭tomcat,我必须杀死进程。有什么想法吗?

关闭tomcat后留下的线程是:

  • 守护程序线程[Thread-2]
  • 线程[事件-1]
  • Thread [DestroyJavaVM]

使用的库和服务器的版本:

  • Apache CXF 3.0.1
  • Spring 4.0.3.RELEASE
  • Spring Security 3.2.0.RELEASE
  • Spring Java-config
  • Apache Tomcat 7.0.47

我的pom.xml与cxf库和servlet-api库有以下依赖关系:

<dependency>
    <groupId>org.apache.cxf</groupId>
    <artifactId>cxf-rt-frontend-jaxws</artifactId>
    <version>3.0.1</version>
</dependency>
<dependency>
    <groupId>org.apache.cxf</groupId>
    <artifactId>cxf-rt-transports-http</artifactId>
    <version>3.0.1</version>
</dependency>
<dependency>
    <groupId>javax.servlet</groupId>
    <artifactId>javax.servlet-api</artifactId>
    <version>3.1.0</version>
    <scope>provided</scope>
</dependency>

这是我在CXFServlet中连接的方式:

@Order(3)
public class IMSWebServicesApplicationInitializer implements WebApplicationInitializer
{
@Override
public void onStartup(ServletContext servletContext) throws ServletException
{
    ServletRegistration.Dynamic servlet = servletContext.addServlet("CXFServlet", new CXFServlet());
    servlet.setLoadOnStartup(1);
    servlet.addMapping("/services/*");
}

以下是我在端点中连线的方式:

import org.apache.cxf.Bus;
import org.apache.cxf.jaxws.EndpointImpl;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.context.annotation.ImportResource;

import com.verisk.underwriting.id_access_api.api.authentication.AuthenticationService;
import com.verisk.underwriting.id_access_api.token.DefaultTokenInfo;
import com.verisk.underwriting.id_access_api.token.TokenService;
import com.verisk.underwriting.ims.web.service.LoginWebService;
import com.verisk.underwriting.ims.web.service.LoginWebServiceImpl;
import com.verisk.underwriting.modules.appbase.status.ServerStatusService;

@Configuration
@ImportResource({"classpath:META-INF/cxf/cxf.xml"})
public class IMSWebServicesConfiguration
{           
    @Bean
    @Autowired
    public EndpointImpl login(Bus bus, LoginWebService loginWebService)
    {       
        EndpointImpl endpointImpl = new EndpointImpl(bus, loginWebService);
        endpointImpl.setAddress("/login");
        endpointImpl.publish();
        return endpointImpl;
    }

    @Bean
    @Autowired
    public LoginWebService loginWebService(TokenService<DefaultTokenInfo> tokenService,     AuthenticationService authenticationService, 
            ServerStatusService<DefaultTokenInfo> serverStatusService)
    {
        return new LoginWebServiceImpl(tokenService, authenticationService,     serverStatusService);
    }
}

LoginWebService接口:

@WebService(name="login")
@SOAPBinding(style=Style.RPC, use=Use.LITERAL)
public interface LoginWebService
{
...
}

LoginWebService实现:

@WebService(endpointInterface="com.verisk.underwriting.ims.web.service.LoginWebService", serviceName="login")
public class LoginWebServiceImpl implements LoginWebService
{ 
...
}

1 个答案:

答案 0 :(得分:1)

您可以take a thread dump处理以下几点:

  1. 在发出shutdown命令之前。
  2. 发出shutdown命令后立即。
  3. 发出shutdown命令后60秒,然后
  4. 关机命令后120秒。
  5. 然后,您可以使用thread analyser tool和/或在公共场所发布转储并在此处分享。

    基本上,我们的想法是找到线程正在做什么以及哪些阻止容器关闭,可能是由于锁定。