以下示例代码在VBA中通过adodb连接运行两个SQL语句时意外无法返回错误
Dim conn As ADODB.Connection
Set conn = return_connection(server:="Database")
test_statement = "Select (1) if 1=1 THROW 50001, 'Error description', 1;"
conn.Execute (test_statement)
然而,运行以下语句
Dim conn As ADODB.Connection
Set conn = return_connection(server:="Database")
test_statement1 = "Select (1)"
test_statement2 = "if 1=1 THROW 50001, 'Error description', 1"
conn.Execute (test_statement1)
conn.Execute (test_statement2)
完美无缺。
此外,如果我复制并粘贴
Select (1) if 1=1 THROW 50001, 'Error description', 1;
进入SQL管理器它的工作原理与我预期的有问题的代码完全相同:做一个选择然后抛出一个错误。
任何人都可以向我解释这个吗?
显然,明显的“解决方案”是将不同的语句分开,以便在VBA中单独运行,我将从现在开始这样做。
但是我显然不明白Adodb如何使用SQL的基本原理所以我想知道是什么导致了这种行为。另外,我有多个非常重要的SQL语句,它们被连接在一起,然后通过Adodb连接传递给SQL,所以我想知道什么时候可以安全地做,什么时候需要重建代码。
答案 0 :(得分:1)
仔细查看您的SQL语句,它是单个语句而不是多个语句,因为没有行分隔符;
。从
test_statement = "Select (1) if 1=1 THROW 50001, 'Error description', 1;"
要
test_statement = "Select (1); if 1=1 THROW 50001, 'Error description', 1;"
此外,如果要执行多个语句,请考虑将所有SQL语句包装在Stored Procedure
而不是
答案 1 :(得分:0)
尝试添加SET NOCOUNT ON;
作为批处理中的第一个语句。这将抑制混淆不期望它们的客户端代码的DONE_IN_PROC
TDS消息(行计数)。 ADO classic因此而臭名昭着(不是ADO.NET的问题)。
或者,您可以使用RecordSet对象并调用NextResult
,直到消耗掉所有结果。
答案 2 :(得分:0)
我最好用ADODB.Command
Dim conn As ADODB.Connection
Set conn = return_connection(server:="Database")
Dim cmd As New ADODB.Command
cmd.ActiveConnection = conn
cmd.CommandText = "Select (1) if 1=1 THROW 50001, 'Error description', 1;"
cmd.CommandType = adCmdText
cmd.Prepared = True
cmd.Execute()
注意:Execute
对象的Command
方法可能返回Recordset
对象:
Dim rs As ADODB.Recordset
Set rs = cmd.Execute()
我尚未测试以上代码,但它基于有效的代码。我使用的是Microsoft ActiveX数据对象v2.0,但是它可以与任何ADODB版本一起使用。在我的代码中,我已将整个代码块包装在BEGIN
... END
SQL块中,并且在每个语句的末尾都包含了分号,尽管我很确定这些是两者都是不必要的。
鼓励改正我的错误,并鼓励提出建议或纠正意见。