我试图仅通过查看 SQL 探查器来调试应用程序错误。(我无权访问代码)。
应用程序中的错误说
现在,我在执行前端命令时运行了 SQL 分析器,并尝试识别未提交的命令。我不能发布确切的查询,但我会发布他们的主要部分。
在以下更新语句之后调用了探查器ROLLBACK
(据我所知,只有 INSERT/UPDATE/DELETE 语句被回滚)。
UPDATE transactions
SET refference = N':ICBilling 8/9/2013'
,type1 = 1
,notes = N'Billing'
,dateModified = convert(DATETIME, N'08/09/2013 10:33:13AM', 101)
,moduleModifiedBy = N'PM'
WHERE transaction_id = 1100001368
我向上滚动分析器以查看之前发生的情况,并观察到该记录已插入到transactions
表中。
INSERT INTO transactions (
transaction_id,
uRefference,
Type1,
Notes,
ModuleModifiedBy,
)
VALUES (
1100001368
, NULL
, 0
, NULL
, convert(DATETIME, N'08/09/2013 10:33:13AM', 101)
)
在此插入之前有一个BEGIN TRANSACTION
命令。我假设由于INSERT
操作没有提交到Transactions
表中,该UPDATE
语句会导致错误,因为它找不到要更新的记录。
(尽管我已经在 SQL Server 中使用这些查询测试了这个想法。我创建了一个临时表并立即运行了该部分begin transaction
)
CREATE TABLE #tempx (i INT);
INSERT INTO #tempx VALUES (1),(2),(3);
BEGIN TRANSACTION
INSERT INTO #tempx VALUES (4);
UPDATE #tempx
SET i = 5
WHERE i = 4
查询运行并且UPDATE
执行没有问题,所以我已经消除了这种可能性。尽管我对直接从 SQL Server MS 运行查询和从应用程序调用它们之间的区别表示怀疑,但在进一步谷歌搜索之后,我发现(这里)必须设置一些参数才能进行隐式事务。
所以,我回到了我的分析器,就在顶部,这就是我发现的
SET QUOTED_IDENTIFIER ON
SET ARITHABORT OFF
SET NUMERIC_ROUNDABORT OFF
SET ANSI_WARNINGS ON
SET ANSI_PADDING ON
SET ANSI_NULLS ON
SET CONCAT_NULL_YIELDS_NULL ON
SET CURSOR_CLOSE_ON_COMMIT OFF
SET IMPLICIT_TRANSACTIONS OFF
SET LANGUAGE us_english
SET DATEFORMAT mdy
SET DATEFIRST 7
SET TRANSACTION ISOLATION LEVEL READ UNCOMMITTED
我还没有尝试设置IMPLICIT_TRANSACTIONS
,ON
因为这是一个生产数据库,我不完全确定不会有问题。
所以,我想请有更多经验的人帮助我找到或至少深入到问题可能出现的地方(代码或 SQL Server 设置中)
更新:
我设法访问了引发错误的代码部分
If Not myExceptionOccured And Not SessionKey Is Nothing Then
If SessionKey.Connection.IsInTranState Then
Dim Message As String = String.Format("Could not complete Page_Unload. There are {0} uncommitted transactions. All changes were rolled back.", SessionKey.Connection.TransactionCount)
所以现在很清楚,会话没有被关闭,事务也没有被 SQL Server 提交。
我已经尝试修改其他交易并且有效。但显然它只有这个交易有问题。我会尝试比较这些交易的两个分析器,也许我能找到不同之处。
同时,如果有人认为我走错了方向,请发表评论。
更新#2:
就像我说的那样,我分析了另一个有效的事务并查看了调用回滚之后的查询。
在这两种情况下(在它工作和回滚的情况下),查询都是这样的(与我的问题开头相同):
UPDATE transactions
SET refference = N':Billing 8/16/2013'
,type1 = 1
,notes = N'Billing'
,dateModified = convert(DATETIME, N'08/16/2013 12:47:25PM', 101)
,moduleModifiedBy = N'PM'
WHERE tranId = --transaction id here--
它们之间的唯一区别是它们更新的事务 ID 和时间(有一个GETDATE()
获取当前时间的函数)。
仅此而已。一项事务已提交,另一项未提交。
还有其他建议吗?