我在生产中有一个存储过程,它做两件事。它更新一个表,然后将一条记录插入到另一个表中。第一步(更新)似乎发生了,但我们通过检查没有发生第二步的数据发现了实例。我查看了数据并确认这不是数据问题。我已经确认查询返回了适当的数据,以确保查询完成并且在正常情况下都应该执行。我不知道是否可能存在某种性能问题......或阻止该步骤发生的第二步发生的阻塞问题。
存储过程的错误处理如下。
BEGIN TRY
BEGIN TRANSACTION;
-- perform update to data
-- insert record into second table.
IF ( @@ERROR = 0 AND @@TRANCOUNT > 0 )
COMMIT TRANSACTION;
END TRY
BEGIN CATCH
IF ( @@TRANCOUNT > 0 )
BEGIN
ROLLBACK TRANSACTION;
END
DECLARE @WebSafeErrorId INT;
EXEC dbo.spErrorInsert @WebSafeErrorId OUTPUT, 'Proc';
-- Reraise the error back to the client.
IF ( @WebSafeErrorId != 0 )
BEGIN
DECLARE @Error VARCHAR(20);
SET @Error = CAST( @WebSafeErrorId AS VARCHAR(20) );
RAISERROR( @Error, 11, 1 );
END
ELSE
BEGIN
RAISERROR( 'An error has occurred but there is no error to log.', 11, 1 );
END
END CATCH;
当然,如果此过程中发生导致插入不发生的错误,它将被记录然后引发。spErrorInsert 的代码如下...
CREATE PROCEDURE [dbo].[spErrorInsert]
@ReturnErrorId INT OUTPUT
, @ErrorSourceType VARCHAR(4) = NULL
, @ParentErrorId INT = NULL
, @StackTrace VARCHAR(MAX) = NULL
AS
SET NOCOUNT ON;
--SET XACT_ABORT ON;
-- Will indicate an error was not logged.
SET @ReturnErrorID = 0;
DECLARE
@ErrorSource VARCHAR(200)
, @ErrorMessage VARCHAR(MAX)
, @ComposedErrorMessage VARCHAR(MAX)
, @ErrorLine INT
, @ErrorSeverity INT
, @ErrorState INT
, @ErrorNumber INT;
SET @ErrorSource = ERROR_PROCEDURE();
SET @ErrorMessage = ERROR_MESSAGE();
SET @ErrorLine = ERROR_LINE();
SET @ErrorSeverity = ERROR_SEVERITY();
SET @ErrorState = ERROR_STATE();
SET @ErrorNumber = ERROR_NUMBER();
SET @ComposedErrorMessage = 'Message: Error occurred in procedure ' + CAST( @ErrorSource AS VARCHAR(MAX) )
+ ' on line ' + CAST( @ErrorLine AS VARCHAR(MAX) )
+ '. Error: ' + @ErrorMessage;
BEGIN TRY
INSERT INTO Errors(
ParentId
, ErrorSourceType
, ErrorSource
, [Message]
, [LineNo]
, Severity
, Stacktrace
, ts)
VALUES (@ParentErrorId
, @ErrorSourceType --@ErrorSourceType --- NOTE: move this into a parameter ...
, @ErrorSource
, @ComposedErrorMessage
, @ErrorLine
, @ErrorState
, @Stacktrace
, GETDATE()
);
SET @ReturnErrorId = SCOPE_IDENTITY();
END TRY
BEGIN CATCH
RAISERROR( 'An error has occurred but there is no error to log.', 11, 1 );
END CATCH;
我不知道是否有办法在调用某个过程的特定时间获取数据库正在发生的事情的快照......我不确定如何确定它是否没有发生应该?有没有我可以使用的工具或我不知道的 sql 功能???