ADODB.Connection InfoMessage 事件永远不会被触发

时间:2021-03-02 06:46:40

标签: sql-server vba ms-access oledb ado

我将此作为新问题发布,因为帖子 Execute SQL Server stored procedure from VBA and retrieve all messages and result sets 中的答案没有解决我的问题。

我使用 MS Access 作为 SQL Server 的前端,并希望从长时间运行的多语句 SQL 过程中获取进度消息,但从未触发 InfoMessage 事件。我在存储过程中放置​​了具有不同严重性级别的 PrintRaiseError 语句。还尝试根据连接和不同的 OLDDB 提供程序(SQLNCLI10、SQLNCLI11、MSOLEDBSQL、SQLOLEDB)执行命令对象

当 sql 过程结束时,ExecuteComplete 事件被正确触发。 pError Parameter 设置为“Executing 1st statement ...”,并且——令人惊讶的是——Connection.Errors 集合包含三个错误:“Executing 1st statement ...”、“Now for a print statement”和“Executing 3rd statement。 ..”

这是我的 SQL 代码:

ALTER PROCEDURE TestCommunication 
AS
BEGIN
    -- SET NOCOUNT ON added to prevent extra result sets from
    -- interfering with SELECT statements.
    SET NOCOUNT ON;

    -- Insert statements for procedure here
    RAISERROR('Executing 1st statement ...', 1, 1) WITH NOWAIT
    WAITFOR DELAY '00:00:05'

    RAISERROR('Executing 2nd statement ...', 10, 10) WITH NOWAIT
    WAITFOR DELAY '00:00:05'

    PRINT 'Now for a Print-statement!'
    WAITFOR DELAY '00:00:03'

    RAISERROR('Executing 3rd statement ...', 16, 16) WITH NOWAIT
    WAITFOR DELAY '00:00:05'

    RAISERROR('Completing ...', 16, 10) WITH NOWAIT
END
GO

这是我的 VBA 代码:

Option Compare Database

Private WithEvents conn As ADODB.Connection

Private Sub conn_ExecuteComplete(ByVal RecordsAffected As Long, ByVal pError As ADODB.Error, adStatus As ADODB.EventStatusEnum, ByVal pCommand As ADODB.Command, ByVal pRecordset As ADODB.Recordset, ByVal pConnection As ADODB.Connection)
    Debug.Print "Execution ended"
End Sub

Private Sub conn_InfoMessage(ByVal pError As ADODB.Error, adStatus As ADODB.EventStatusEnum, ByVal pConnection As ADODB.Connection)
    Debug.Print pError.Description
End Sub

Public Sub RunQuery(strQuery As String)

    Set conn = New ADODB.Connection
    conn.ConnectionString = getADODBConnectionString        'Provider=SQLOLEDB;Server=adgpcr.res2.loc.lan.at;Database=CostDB;Integrated Security=SSPI;APP=CostDB;
    conn.Open
    conn.Execute strQuery, , adExecuteNoRecords + adAsyncExecute

End Sub
Public Sub TestMessages()
    
    Set o = New ADODBQuery    'ADODBQuery is the name of the class above
    o.RunQuery "dbo.TestCommunication"

End Sub

按照 Erik A 的建议,我添加了通过命令对象运行存储过程的功能:

Public Sub RunProcedure(strProcedureName As String)

    Set conn = New ADODB.Connection
    conn.ConnectionString = getADODBConnectionString
    conn.Open
    
    Dim cmd As ADODB.Command
    Set cmd = New ADODB.Command
    cmd.CommandType = adCmdStoredProc
    cmd.CommandText = strProcedureName
    cmd.ActiveConnection = conn
    
    cmd.Execute , , adExecuteNoRecords + adAsyncExecute

End Sub

与从连接对象执行存储过程的结果相同。

有趣的事实:当省略选项 adExecuteNoRecords + adAsyncExecute 时,ExecuteComplete 事件被立即触发(预期),然后 InfoMessage 事件被触发一次(!),pError 和连接对象的 Errors 集合设置为第一个 RAISERROR 消息! ?!

对我遗漏的东西有什么意见吗?

0 个答案:

没有答案
相关问题