【发布时间】:2019-12-10 15:20:35
【问题描述】:
我有一个 PHP 程序,它使用 PDO::sqlsrv 驱动程序来查询 MS SQL Server 数据库。
这有一些奇怪的行为。如果我启用了 MARS (https://docs.microsoft.com/en-us/sql/relational-databases/native-client/features/using-multiple-active-result-sets-mars?view=sql-server-ver15),这是默认设置,并尝试在某些时候启动事务,我会收到以下错误:
["42000",3988,"[Microsoft][ODBC Driver 17 for SQL Server][SQL Server]New transaction is not allowed because there are other threads running in the session."]
这似乎是因为一些活动的结果集需要关闭。不幸的是,我不知道如何确定会话中正在运行哪些线程。我关闭了 MARS 以尝试更好地确定哪些查询没有正确关闭,并且在任何插入/更新后我收到以下错误:
IMSSP
-61
The connection cannot process this operation because there is a statement with pending results. To make the connection available for other queries, either fetch all results or cancel or free the statement. For more information, see the product documentation about the MultipleActiveResultSets connection option.
显然任何插入/更新都会创建一个需要关闭其游标的结果集。
在每个 DML 语句修复问题后手动关闭游标。这很不方便,而且似乎不应该是 SQL Server 的行为来创建无意义的结果集(DML 语句不返回任何行)。
这是预期的行为(DML 语句需要手动关闭关联的游标)吗?
有没有办法阻止这种行为(DML 语句自动关闭游标)?
有没有办法关闭连接上所有打开的结果集,以便我可以启动事务(这很容易实现)?
【问题讨论】:
-
看来您应该在此处发布您的 PHP 代码并对其进行标记,以便我们了解您正确处理连接的原因,
-
DML 不创建结果集,除非是 OUTPUT 子句,或者触发器返回结果集。您将收到 DONE_IN_PROC 消息,除非您 SET NOCOUNT ON,并且某些客户端堆栈不会自动处理 DONE_IN_PROC 消息。
-
@DavidBrowne-Microsoft 尝试从结果语句中获取任何内容不会返回任何内容;但似乎结果上有一个打开的光标(直到它被手动关闭)。
-
可能是这样,具体取决于客户端驱动程序的实现方式。
标签: sql-server tsql pdo sqlsrv