gpt4 book ai didi

java - 我没有在 Tomcat 中的 Web 应用程序的线程中获取 Hibernate session

转载 作者:行者123 更新时间:2023-11-28 22:42:31 25 4
gpt4 key购买 nike

我有一个带有 Tomcat 的 Web 应用程序。我正在使用一些线程而不是在 Controller 中执行。在这个线程中我执行其他线程。

这个线程需要与 Hibernate 有一个 session ,但是当我执行一些查询时它不工作,尽管我在每个线程的“运行”方法中打开一个新 session 。

当我在 Tomcat 外部执行这段代码时,它就像一个简单的 java main.所以,看起来这是我对 Tomcat 做错的事情。 我猜可能是因为 OpenSessionInViewFilter。我收到有关当前线程没有 session 的错误消息。

我得到的异常是:

org.hibernate.HibernateException: No Session found for current thread
at org.springframework.orm.hibernate4.SpringSessionContext.currentSession(SpringSessionContext.java:97)
at org.hibernate.internal.SessionFactoryImpl.getCurrentSession(SessionFactoryImpl.java:941)

我的 web.xml

<filter>
<filter-name>sessionView</filter-name>
<filter-class>
org.springframework.orm.hibernate4.support.OpenSessionInViewFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>sessionView</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>

我的 Controller

 @Override
protected ModelAndView onSubmit(final HttpServletRequest request,
final HttpServletResponse response, final Object command, final BindException errors)
throws Exception {
MyThread thread = new ExecuteETLThread();
thread.start();
...
}

我的线程:

public final class MyThread extends AbstracThread {

@Override
public void runThread() {
try {
//I get an exception here. I just put this senstence here for checking.
context.getConfigurationDAO().get("A");
//Normally, I open more threads here that they connect with hibernate and fail.
//otherThread.start();
} catch (final Exception e) {
LOG.error(e);
}
}

抽象线程:

public abstract class AbstractThread extends Thread {
@Override
public final void run() {
try {
OpenSessionInView.openSession();
runThread();
} catch (final Exception e) {
LOG.error("Error running BidoopThread", e);
} finally {
OpenSessionInView.closeSession();
}
}
public abstract void runThread();
}

使用 Hibernate 打开 session 。

public final class OpenSessionInView {
public static void openSession() {
final SessionFactory sf = Factory.getSessionFactory();

final Session session = sf.openSession();
session.setFlushMode(FlushMode.COMMIT);
TransactionSynchronizationManager.bindResource(sf, new SessionHolder(session));
}

public static void closeSession() {
final SessionFactory sf = Factory.getSessionFactory();
final SessionHolder sessionHolder =
(SessionHolder) TransactionSynchronizationManager.unbindResource(sf);
SessionFactoryUtils.closeSession(sessionHolder.getSession());
}

最佳答案

OpenSessionInViewFilter 和 spring 的 EntityManager 委托(delegate)都使用 ThreadLocal 来存储真正的 EntityManager 实现。每次发起请求时,他们都会在此请求的线程中将 EntityManager 绑定(bind)到此 ThreadLocal。因此 EM 不会绑定(bind)到您手动创建的线程。您应该观察您的堆栈跟踪并找出 spring 在哪里寻找 EM(或 session )。根据您提供的堆栈跟踪,学习 SpringSessionContext 以找到手动绑定(bind) session 的方法。您还需要执行一些工作以在线程完成时清理 session 。

关于java - 我没有在 Tomcat 中的 Web 应用程序的线程中获取 Hibernate session ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24989925/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com