DbGraphConnectionLocator

DbGraphConnectionLocator

我有一个带有注释的on Object

@ApplicationScoped
public class DbGraphConnectionLocator implements ServerStopTask {
...
}


该对象创建一个嵌入式数据库。

当我重新部署应用程序时,我试图创建一个挂钩来关闭数据库。

所以我建立了课程

@WebListener
public class UndeployHook implements ServletContextListener{
@Inject
DbGraphConnectionLocator dbGraphConnectionLocator;


@Override
public void contextInitialized(ServletContextEvent servletContextEvent) {

}

@Override
public void contextDestroyed(ServletContextEvent servletContextEvent) {
    try {
        dbGraphConnectionLocator.executeStopTask();
        } catch (Exception e) {
        e.printStackTrace();
        }
    }
}


实际上,调用了contextDestoyed方法,但是其中使用的对象不是启动时创建的原始DbGraphConnectionLocator,这给我带来了麻烦。

我认为带有注释

@ApplicationScoped
public class DbGraphConnectionLocator implements ServerStopTask { ....}


DbGraphConnectionLocator的实例在应用程序级别必须是唯一的,因此当我将其与

@Inject
DbGraphConnectionLocator dbGraphConnectionLocator;


我必须找到由我的应用程序启动时创建的同一实例,但这不是事实,已创建另一个实例。

无论如何我决定添加

@PreDestroy
public  void shutdownDB(){
    graphDb.shutdown();
}


到DbGraphConnectionLocator。
对于信息,我看到此方法在contextDestroyed方法之后被调用,这意味着当调用contextDestroyed时,原始实例仍然存在,所以我错过了一些东西。

有什么提示吗?

最佳答案

如果嵌入式数据库应在应用程序启动时创建,并在应用程序停止时关闭,则请执行以下操作:


@ApplicationScoped
@Startup
public class AnyNameForYourApplicationClass {

  @PostConstruct
  public void connectDB() {
    // creates the db connection at startup
  }

  @PreDestoy
  public void disconnectDB() {
    // disconnects from the db
  }
}


这应该做。
或者,您也可以使用CDI生产者来创建应用程序范围的db连接。然后,您可以使用处理程序方法从数据库断开连接。

在您的情况下,此行为是正确的,因为在调用Web侦听器时,该应用程序必须仍然处于活动状态。因此,在销毁应用程序作用域的bean之后,将使用@PreDestroy调用shutdownDB方法。并且由于您是在侦听器中引用它,因此它必须一直存在,直到侦听器被销毁为止。

09-05 16:17