ODP.NET托管ConnectionPool每3分钟关闭/打开一次

Jon*_*kum 5 oracle connection-pooling odp.net odp.net-managed

我们正在使用从Oracle到Oracle 12数据库(非RAC)配置的最新官方ODP.NET托管(已发布:2015-10-14 |版本:12.1.2400),我们无法保持数据库连接的活动范围超过典型值<3分钟.

我们的连接字符串指定

MAX POOL SIZE=10;MIN POOL SIZE=5;INCR POOL SIZE=1;
Run Code Online (Sandbox Code Playgroud)

我们也试过了

CONNECTION LIFETIME=90000;MAX POOL SIZE=10;MIN POOL SIZE=5;INCR POOL SIZE=1;
Run Code Online (Sandbox Code Playgroud)

当我们在服务器上使用PerfMon并观察HardConnects/HardDisconnects的计数器时,我们认为连接池关闭并每3分钟重新打开5个连接,这不是我们所期望的.

我们在使用EF6 for DataAccess的webapp和没有ORM的应用程序(只是普通的旧SQL)中都有这种行为.

根据Oracle文档:

连接池服务在不使用时关闭连接; 连接每3分钟关闭一次.ConnectionString属性的Decr Pool Size属性为每3分钟可以关闭的最大连接数提供连接池服务.

对我来说 - 只要连接在生命周期限制内,连接池中的有效连接的MIN POOL SIZE持续时间要长于3分钟.

我们有另一个使用Devart的Oracle驱动程序的应用程序,这个驱动程序汇集了长时间保持活动状态的连接.

有没有人在ODP.NET托管驱动程序中看到ConnectionPool的这种"不当行为"并找到了解决方案?或者这可能是ODP.NET Managed的ConnectionPool中的错误?

更新2016.01.27:

我在我的github帐户上添加了一个演示应用程序来演示此问题:

https://github.com/jonnybee/OraConnTest

这只是一个小的winforms应用程序,您可以在其中添加连接字符串,然后单击按钮以启动后台工作程序,每3秒运行一次"SELECT'OK'INF DUAL".

我的连接字符串包含:POOLING = True; MAX POOL SIZE = 10; DECR POOL SIZE = 1; CONNECTION LIFETIME = 86400; INCR POOL SIZE = 1; MIN POOL SIZE = 5 +您必须添加USER ID,PASSWORD和DATA SOURCE.

每隔3分钟,您将看到5个现有连接已关闭,并创建了5个新连接(MIN POOL SIZE设置).

运行此SQL以查看实际连接:从v $ session选择sid,logon_time,prev_exec_start,wait_time_micro/1000,其中程序如'%OraWinApp%'按logon_time desc排序

当程序和perfmon正在运行时,您将看到此行为,因为旧连接已关闭,并且创建了与新login_time的新连接.

b_l*_*itt 1

我同意你对它应该如何工作的评估,但 ODP.net 中的连接池有点奇怪。这里的关键是,连接生存期仅在“应用程序关闭连接时”被遵守,其中 decr 池大小似乎有自己的线程。我不知道他们为什么这样做 - 仅在返回池时进行验证会创建一个 senario,您可以在其中将死连接(由防火墙超时终止)从池中拉出。

我实际上设置了最小池大小=0。这可确保应用程序空闲时池为空。我几乎可以保证,除非您的网络速度非常慢或者已经有一个已经超载的 Oracle 实例,否则您不会注意到其中的差异。连接池很重要,但通常只需几毫秒即可建立连接。

唯一让我失望的是所有 5 个连接都已关闭 - decr 池大小默认为 1。