处理生成消息的语句
适用于:SQL Server Azure SQL 数据库 Azure SQL 托管实例 Azure Synapse Analytics Analytics Platform System (PDW)
Transact-SQL SET 语句选项 STATISTICS TIME 和 STATISTICS IO 用于获取有助于诊断长时间运行的查询的信息。 早期版本的 SQL Server 还支持 SHOWPLAN 选项来分析查询计划。 ODBC 应用程序可通过执行以下语句设置这些选项:
SQLExecDirect(hstmt, "SET SHOWPLAN ON", SQL_NTS);
SQLExecDirect(hstmt, "SET STATISTICS TIME ON", SQL_NTS90
);
SQLExecDirect(hstmt, "SET STATISTICS IO ON", SQL_NTS);
当 SET STATISTICS TIME 或 SET SHOWPLAN 为 ON 时,SQLExecute 和 SQLExecDirect 返回SQL_SUCCESS_WITH_INFO,此时应用程序可以通过调用 SQLGetDiagRec 来检索 SHOWPLAN 或 STATISTICS TIME 输出,直到返回SQL_NO_DATA。 SHOWPLAN 数据的每一行均按以下格式返回:
szSqlState="01000", *pfNativeError=6223,
szErrorMsg="[Microsoft][SQL Server Native Client][SQL Server]
Table Scan"
SQL Server 版本 7.0 将 SHOWPLAN 选项替换为SHOWPLAN_ALL和SHOWPLAN_TEXT,这两个选项都返回结果集的输出,而不是一组消息。
STATISTICS TIME 的每一行均按以下格式返回:
szSqlState="01000", *pfNativeError= 3613,
szErrorMsg="[Microsoft][SQL Server Native Client][SQL Server]
SQL Server Parse and Compile Time: cpu time = 0 ms."
在到达结果集的末尾之前,SET STATISTICS IO 的输出不可用。 若要获取 STATISTICS IO 输出,应用程序在 SQLFetch 或 SQLFetchScroll 返回SQL_NO_DATA时调用 SQLGetDiagRec。 STATISTICS IO 的输出按以下格式返回:
szSqlState="01000", *pfNativeError= 3615,
szErrorMsg="[Microsoft][ SQL Server Native Client][SQL Server]
Table: testshow scan count 1, logical reads: 1,
physical reads: 0."
使用 DBCC 语句
DBCC 语句将其数据作为消息(而不是结果集)返回。 SQLExecDirect 或 SQLExecute 返回SQL_SUCCESS_WITH_INFO,应用程序通过调用 SQLGetDiagRec 来检索输出,直到它返回SQL_NO_DATA。
例如,下面的语句返回 SQL_SUCCESS_WITH_INFO:
SQLExecDirect(hstmt, "DBCC CHECKTABLE(Authors)", SQL_NTS);
对 SQLGetDiagRec 的 调用返回:
szSqlState = "01000", *pfNativeError = 2536,
szErrorMsg="[Microsoft][ SQL Server Native Client][SQL Server]
Checking authors"
szSqlState = "01000", *pfNativeError = 2579,
szErrorMsg="[Microsoft][ SQL Server Native Client][SQL Server]
The total number of data pages in this table is 1."
szSqlState = "01000", *pfNativeError = 7929,
szErrorMsg="[Microsoft][ SQL Server Native Client][SQL Server]
Table has 23 data rows."
szSqlState = "01000", *pfNativeError = 2528
szErrorMsg="[Microsoft][ SQL Server Native Client][SQL Server]
DBCC execution completed. If DBCC printed error messages,
see your System Administrator."
使用 PRINT 和 RAISERROR 语句
Transact-SQL PRINT 和 RAISERROR 语句还通过调用 SQLGetDiagRec 返回数据。 PRINT 语句导致 SQL 语句执行返回SQL_SUCCESS_WITH_INFO,对 SQLGetDiagRec 的后续调用返回 SQLState 为 01000。 严重性为 10 或更低的 RAISERROR 在行为上与 PRINT 相同。 严重性为 11 或更高的 RAISERROR 会导致执行返回SQL_ERROR,对 SQLGetDiagRec 的后续调用将返回 SQLState 42000。 例如,下面的语句返回 SQL_SUCCESS_WITH_INFO:
SQLExecDirect (hstmt, "PRINT 'Some message' ", SQL_NTS);
调用 SQLGetDiagRec 返回:
szSQLState = "01000", *pfNative Error = 0,
szErrorMsg= "[Microsoft] [SQL Server Native Client][SQL Server]
Some message"
下面的语句返回 SQL_SUCCESS_WITH_INFO:
SQLExecDirect (hstmt, "RAISERROR ('Sample error 1.', 10, -1)",
SQL_NTS)
调用 SQLGetDiagRec 返回:
szSQLState = "01000", *pfNative Error = 50000,
szErrorMsg= "[Microsoft] [SQL Server Native Client][SQL Server]
Sample error 1."
下面的语句返回 SQL_ERROR:
SQLExecDirect (hstmt, "RAISERROR ('Sample error 2.', 11, -1)", SQL_NTS)
调用 SQLGetDiagRec 返回:
szSQLState = "42000", *pfNative Error = 50000,
szErrorMsg= "[Microsoft] [SQL Server Native Client][SQL Server]
Sample error 2."
当 PRINT 或 RAISERROR 语句的输出包含在结果集中时,调用 SQLGetDiagRec 的计时至关重要。 在 接收SQL_ERROR或SQL_SUCCESS_WITH_INFO的语句之后,必须立即调用 SQLGetDiagRec 来检索 PRINT 或 RAISERROR 输出。 当仅执行一个 SQL 语句时(如上述示例中所示),这非常简单。 在这些情况下,调用 SQLExecDirect 或 SQLExecute 将返回SQL_ERROR或SQL_SUCCESS_WITH_INFO,然后可以调用 SQLGetDiagRec。 当编码循环处理一批 SQL 语句的输出或执行 SQL Server 存储过程时,它不太简单。
在这种情况下,SQL Server 为批处理或存储过程中执行的每个 SELECT 语句返回结果集。 如果批处理或过程包含 PRINT 或 RAISERROR 语句,它们的输出将与 SELECT 语句结果集交叉。 如果批处理或过程中的第一个语句是 PRINT 或 RAISERROR, 则 SQLExecute 或 SQLExecDirect 将返回SQL_SUCCESS_WITH_INFO或SQL_ERROR,并且应用程序需要调用 SQLGetDiagRec ,直到返回SQL_NO_DATA来检索 PRINT 或 RAISERROR 信息。
如果 PRINT 或 RAISERROR 语句位于 SQL 语句(如 SELECT 语句)之后,则当 SQLMoreResults 位于包含错误的结果集上时,将返回 PRINT 或 RAISERROR 信息。 SQLMoreResults 根据消息的严重性返回SQL_SUCCESS_WITH_INFO或SQL_ERROR。 通过调用 SQLGetDiagRec 来检索消息,直到它返回SQL_NO_DATA。