简介
SpringSessionContext 是Spring框架中与Hibernate 5集成的一个类。该类实现了Hibernate的SessionContext接口,用于在Spring管理的环境中管理Hibernate的Session。
在Spring和Hibernate集成时,SpringSessionContext允许Hibernate的Session与Spring管理的应用上下文(Application Context)进行交互。通过SpringSessionContext,Hibernate的Session可以获取与Spring管理的Bean相同的生命周期,这意味着Session可以在需要时由Spring自动创建,并在不再需要时自动关闭。
SpringSessionContext的主要用途之一是支持Open Session in View模式,即在整个Web请求的生命周期内保持Hibernate的Session打开。这有助于避免懒加载异常,因为视图渲染过程中可能需要访问尚未加载的关联实体。
然而,需要注意的是,SpringSessionContext本身并不直接依赖于Spring Security。它更多地是与Spring的核心容器和事务管理功能进行交互。Spring Security是一个提供身份验证、授权等安全特性的框架,而SpringSessionContext主要关注于Hibernate Session的生命周期管理。
虽然SpringSessionContext和Spring Security可能同时在同一个Spring应用程序中使用,但它们各自服务于不同的目的,并且没有直接的依赖关系。在配置Hibernate与Spring集成时,可以使用SpringSessionContext来管理Session的生命周期,而Spring Security则用于处理与安全性相关的方面。
总结来说,org.springframework.orm.hibernate5.SpringSessionContext是Spring框架中与Hibernate 5集成的一个类,用于在Spring管理的环境中管理Hibernate的Session生命周期,但它与Spring Security没有直接的依赖关系。
源码
public class SpringSessionContext implements CurrentSessionContext {
private final SessionFactoryImplementor sessionFactory;
@Nullable
private TransactionManager transactionManager;
@Nullable
private CurrentSessionContext jtaSessionContext;
/**
* Create a new SpringSessionContext for the given Hibernate SessionFactory.
* @param sessionFactory the SessionFactory to provide current Sessions for
*/
public SpringSessionContext(SessionFactoryImplementor sessionFactory) {
this.sessionFactory = sessionFactory;
try {
JtaPlatform jtaPlatform = sessionFactory.getServiceRegistry().getService(JtaPlatform.class);
this.transactionManager = jtaPlatform.retrieveTransactionManager();
if (this.transactionManager != null) {
this.jtaSessionContext = new SpringJtaSessionContext(sessionFactory);
}
}
catch (Exception ex) {
LogFactory.getLog(SpringSessionContext.class).warn(
"Could not introspect Hibernate JtaPlatform for SpringJtaSessionContext", ex);
}
}
/**
* Retrieve the Spring-managed Session for the current thread, if any.
*/
@Override
@SuppressWarnings("deprecation")
public Session currentSession() throws HibernateException {
//从当前事务线程中获取Session
Object value = TransactionSynchronizationManager.getResource(this.sessionFactory);
//如果value 是Session类型 则直接返回
if (value instanceof Session) {
return (Session) value;
}
//如果value 类型是SessionHolder
else if (value instanceof SessionHolder) {
// HibernateTransactionManager
//将value 转换为SessionHolder 是Session的一个持有者或者是对Session的一中封装
SessionHolder sessionHolder = (SessionHolder) value;
//获取session
Session session = sessionHolder.getSession();
//当前session与当前事务不同步 && 当前线程有一个活动的事务同步
if (!sessionHolder.isSynchronizedWithTransaction() &&
TransactionSynchronizationManager.isSynchronizationActive()) {
//则将改sessionHolder绑定到当前线程中
TransactionSynchronizationManager.registerSynchronization(
new SpringSessionSynchronization(sessionHolder, this.sessionFactory, false));
//并且设置session与当前事务同步
sessionHolder.setSynchronizedWithTransaction(true);
// Switch to FlushMode.AUTO, as we have to assume a thread-bound Session
// with FlushMode.MANUAL, which needs to allow flushing within the transaction.
//获取当前事务刷新缓存的方式
FlushMode flushMode = SessionFactoryUtils.getFlushMode(session);
//显示调用session.flush方法 && 并且当前事务不是只读事务
if (flushMode.equals(FlushMode.MANUAL) &&
!TransactionSynchronizationManager.isCurrentTransactionReadOnly()) {
//则将当前事务刷新缓存的方式设置为自动刷新
session.setFlushMode(FlushMode.AUTO);
//保留之前的方式
sessionHolder.setPreviousFlushMode(flushMode);
}
}
return session;
}
else if (value instanceof EntityManagerHolder) {
// JpaTransactionManager
//value 是EntityManager 则从EntityManager中获取Session
return ((EntityManagerHolder) value).getEntityManager().unwrap(Session.class);
}
//使用jtaSessionContext获取session,并且将session绑定到当前事务线程中
if (this.transactionManager != null && this.jtaSessionContext != null) {
try {
if (this.transactionManager.getStatus() == Status.STATUS_ACTIVE) {
Session session = this.jtaSessionContext.currentSession();
if (TransactionSynchronizationManager.isSynchronizationActive()) {
TransactionSynchronizationManager.registerSynchronization(
new SpringFlushSynchronization(session));
}
return session;
}
}
catch (SystemException ex) {
throw new HibernateException("JTA TransactionManager found but status check failed", ex);
}
}
//如果上述都不符合条件 则通过sessionFactory获取session,并将其他绑定到当前线程事务中
if (TransactionSynchronizationManager.isSynchronizationActive()) {
Session session = this.sessionFactory.openSession();
if (TransactionSynchronizationManager.isCurrentTransactionReadOnly()) {
session.setFlushMode(FlushMode.MANUAL);
}
SessionHolder sessionHolder = new SessionHolder(session);
TransactionSynchronizationManager.registerSynchronization(
new SpringSessionSynchronization(sessionHolder, this.sessionFactory, true));
TransactionSynchronizationManager.bindResource(this.sessionFactory, sessionHolder);
sessionHolder.setSynchronizedWithTransaction(true);
return session;
}
else {
throw new HibernateException("Could not obtain transaction-synchronized Session for current thread");
}
}
}