我需要在每次数据库操作之前设置一些上下文(我尝试使用Oracle的包级变量,但是由于包重新编译的一些问题,我将尝试使用DBMS_SESSION和/或DBMS_APPLICATION_INFO),以便我们可以在任何地方获取特定的用户信息我们需要它(程序,触发器等),而不是将数十个数据库连接标识为“JBoss”.
我编写了一个Java EE拦截器来拦截对@Stateless bean的调用.它调用Oracle函数来设置一些会话上下文(对于一些示例代码How to tell if a transaction is active in a Java EE 6 interceptor,请查看此问题).
我的第一个担心是连接池.起初我认为Java EE提供的默认@PersistenceContext传播足以保证一切都在同一个连接/事务/ EntityManager中运行,而我只需要在拦截器的末尾取消设置所有内容(在finally块中)在连接返回池之前.它似乎有点脆弱,但我认为它可以工作.
然后我发现Hibernate有一个名为hibernate.connection.release_mode的属性
(Hibernate docs about hibernate.connection.release_mode,Red Hat docs about org.hibernate.ConnectionReleaseMode)并且使用JTA事务时的默认和推荐行为是在每个语句之后释放连接(尽管文档说的是重新获取相同的底层连接,这让我很困惑).
现在我甚至不确定我是否可以在拦截器中可靠地设置一些只对这个用户/操作可见的东西,而没有其他人在我的业务方法中抓取相同连接并弄乱我的用户上下文的风险.据我了解,Oracle数据库会话变量是为连接而不是为事务或@PersistenceContext保留的(毕竟数据库对持久化上下文一无所知,并且连接可以用于多个事务).
我即将放弃,因为随着我对所涉及的所有技术的实施细节的了解越来越多,这看起来越来越脆弱.这个用户上下文的想法是可以工作还是我应该尝试一种完全不同的方法?我怎么能测试/调试我的实现,以确保没有潜伏的并发问题?我没有找到任何有用的事件监听器来监视框架行为,并且构建一个程序来对服务器进行压力测试是太多的工作来投资一些我不确定应该工作的东西.
我正在使用JBoss AS 7.1,EJB 3.1,Oracle 10g数据库和JPA 2.0(由Hibernate支持,尽管我们不使用任何特定于Hibernate的API).