防止ADO连接SQL Server时的隐式连接

系统 2004 0

防止 ADO 连接 SQL Server 时的隐式连接

Report Date    2002/9

Prepared by                 

Article last modified on 2002-9

The information in this article applies to:

ü          Microsoft SQL Server 2000,7.0

ü          Microsoft ADO 2.5

问题陈述 :

数据库服务器: Microsoft SQL Server 2000 以及 7.0

数据库服务器补丁: Microsoft SQL Server 2000 ServicePack1

ADO 名称: Microsoft Data Access - ActiveX Data Objects 2.5 Type Library

ADO 版本: 2.61.7326.0

 

执行下面的 VB 代码时,我们的开发人员产生了疑问:

 cnn.Open "Provider=SQLOLEDB.1;

Persist Security Info=False;User ID=sa;

Initial Catalog=freemail;Data Source=svr;ConnectionTimeout=10", "", "", -1
       sql = "select * from users"

    Set rs = cnn.Execute(sql)
       Set rs2 = cnn.Execute(sql)
       Set rs3 = cnn.Execute(sql)

执行这段代码时,在 SQL Server Profiler 中看到,每个 sql 语句执行之前都会有一个 Audit Login 事件。而 Audit Login 事件的解释是:“ 收集自跟踪启动后发生的所有新的连接事件,例如客户端请求连接到运行 Microsoft® SQL Server™ 实例的服务器 。也就是说,用 Connection 对象连接 SQL Server 之后,每次执行 sql 语句时仍然会重新建立一次连接,即使用的是同一个 Connection ?!

建立连接的事件探查记录 ( 按时间顺序 ) 为:

 

EventClass

Text Data

TraceStart

 

Audit Login

( 第一次连接 )

-- network protocol: LPC

set quoted_identifier on

set implicit_transactions off

set cursor_close_on_commit off

set ansi_warnings on

set ansi_padding on

set ansi_nulls on

set concat_null_yields_null on

set language 简体中文

set dateformat ymd

set datefirst 7

SQL:Stm tStarting

Select * from users

Audit Login

( 2 次连接 )

-- network protocol: LPC

set quoted_identifier on

set implicit_transactions off…

SQL:Stm tStarting

Select * from users

Audit Login

( 3 次连接 )

-- network protocol: LPC

set quoted_identifier on

set implicit_transactions off…

SQL:Stm tStarting

Select * from users

Audit Logout

 

Audit Logout

 

Audit Logout

 

TraceStop

 

 

而如果每句 cnn.Execute 后面加上 rs.close() 则每个 execute 之前不会有 Audit Login 事件,而是连续的 3 SQL:StmtStarting 事件。

这样频繁建立物理连接,是否会影响性能?照例说应该重用同一个连接才对呀?

Cause:

这种情况叫做隐式登录。

set 一个 ADO.Recordset 对象接收 ADO.Connection.Execute 返回的记录集时,就会出现隐式登录,再次和数据库服务器建立一次物理连接,而且这个连接还没有办法重用,也不能池化。

这个的原因是:

Because the SQL Server OLE DB provider doesn't permit more than one set of results to be pending on a connection where the results are being returned by means of a forward-only, read-only (default-resultset) cursor, the provider needs to create an additional SQL Server connection to execute a second command on the connection. The provider will only do this implicitly if the Data Source property DBPROP_MULTIPLECONNECTIONS is set to VARIANT_TRUE.

 

可以参考微软的 KB 文档:

http://support.microsoft.com/default.aspx?scid=kb;EN-GB;q271128&GSSNB=1

PRB: Implicit Connections Created by the SQL Server OLE DB Provider (SQLOLEDB) Are Not Pooled

 

【不会重复建立数据库连接的代码片断】:

 

通过改变 ADO.Recordset 的属性避免隐式登录  

Dim cn As New ADODB.Connection
Dim rs As New ADODB.Recordset
Dim rs2 As New ADODB.Recordset
cn.open ..........

 

rs.CursorType = adOpenStatic

rs.ActiveConnection = cn
rs.Open "select * from orders"

rs.CursorType = adOpenStatic
rs2.ActiveConnection = cn
rs2.Open "select * from orders"

看来,确实如微软所说的,只有接收默认的记录集时才会发生隐式连接。如果设置 ADO.Recordset 为其它类型,如静态集,就不会发生这个问题。

当然,默认的记录集的属性 forward-only read-only 情况执行速度最快。

 

Writen by zhengyun@tomosoft.com

 

本文档所包含的信息代表了在发布之日, ZhengYun 对所讨论问题的当前看法, Zhengyun 不保证所给信息在发布之日以后的准确性。

本文档仅供参考。对本文档中的信息, Zhengyun 不做任何明示或默示的保证。

Trackback: http://tb.blog.csdn.net/TrackBack.aspx?PostId=12694


防止ADO连接SQL Server时的隐式连接


更多文章、技术交流、商务合作、联系博主

微信扫码或搜索:z360901061

微信扫一扫加我为好友

QQ号联系: 360901061

您的支持是博主写作最大的动力,如果您喜欢我的文章,感觉我的文章对您有帮助,请用微信扫描下面二维码支持博主2元、5元、10元、20元等您想捐的金额吧,狠狠点击下面给点支持吧,站长非常感激您!手机微信长按不能支付解决办法:请将微信支付二维码保存到相册,切换到微信,然后点击微信右上角扫一扫功能,选择支付二维码完成支付。

【本文对您有帮助就好】

您的支持是博主写作最大的动力,如果您喜欢我的文章,感觉我的文章对您有帮助,请用微信扫描上面二维码支持博主2元、5元、10元、自定义金额等您想捐的金额吧,站长会非常 感谢您的哦!!!

发表我的评论
最新评论 总共0条评论