使用Try Catch从已存储过程中的表中删除不存在的记录显示已成功完成

时间:2016-12-09 12:18:03

标签: sql-server stored-procedures try-catch sql-delete

好吧,我现在正在拉扯我的头发。花了将近10个小时,但却无法理解。我正在尝试编写一个T-SQL存储过程来删除与输入数据匹配的2个表中的记录,如果删除成功则打印一条消息并提交事务,如果没有找到记录,则回滚事务并使用试着抓。我已经编写了下面的代码,但问题是即使数据与输入不匹配,我仍然会得到“命令已成功完成”。信息!感谢您的帮助以解决我的错误。到目前为止,我的代码看起来像这样:

Use Northwind
Go

Create Procedure uspDeleteOrder
@orderID int As 
Set nocount on    
If Exists (Select * from Orders Where OrderID = @orderID)
Begin Try   
    Begin Transaction   
        Delete From dbo.[Order Details]
        Where dbo.[Order Details].OrderID = @orderID    
        Delete From Orders
        Where OrderID = @orderID   
    COMMIT TRANSACTION
    Print 'The article has been deleted!'
End Try
Begin Catch
    IF (@@trancount > 0)
    Begin           
        ROLLBACK TRANSACTION
    End
 PRINT '*************Error Detail****************'
 PRINT 'Error Number  :' + CAST(ERROR_NUMBER() AS VARCHAR)
 PRINT 'Error Severity:' + CAST(ERROR_SEVERITY() AS VARCHAR)
 PRINT 'Error State   :' + CAST(ERROR_STATE() AS VARCHAR)
 PRINT 'Error Line    :' + CAST(ERROR_LINE() AS VARCHAR)
 PRINT 'Error Message :' + ERROR_MESSAGE()
End Catch

Exec uspDeleteOrder 11077

更新:好的,我把我的代码编辑到了这个,我猜这个工作差不多,但我不确定这是不是正确的做法:

Create Procedure uspDeleteOrder
@orderID int As 
Set nocount on    
If Exists (Select * from Orders Where OrderID = @orderID)
Begin
    Begin Try   
        Begin Transaction   
            Delete From dbo.[Order Details]
            Where dbo.[Order Details].OrderID = @orderID    
            Delete From Orders
            Where OrderID = @orderID   
        COMMIT TRANSACTION
        Print 'The Order has been deleted!'
        return
    End Try
    Begin Catch
        IF (@@trancount > 0)
        Begin           
            ROLLBACK TRANSACTION
            RAISERROR ('Error', 16,1); 
        End
        PRINT '*************Error Detail****************'
        PRINT 'Error Number  :' + CAST(ERROR_NUMBER() AS VARCHAR)
        PRINT 'Error Severity:' + CAST(ERROR_SEVERITY() AS VARCHAR)
        PRINT 'Error State   :' + CAST(ERROR_STATE() AS VARCHAR)
        PRINT 'Error Line    :' + CAST(ERROR_LINE() AS VARCHAR)
        PRINT 'Error Message :' + ERROR_MESSAGE()
    End Catch
End
Else 
Begin
    RAISERROR ('No Order ID', 16,1);
End

有什么意见吗?

3 个答案:

答案 0 :(得分:0)

你需要从Catch Block中获得RAISERROR。

目前您正在捕获错误并选择错误详细信息,但存储过程仍然会返回成功。

添加一行

RAISERROR ('Err', 16,1); 

到catch块

答案 1 :(得分:0)

那么如果没有删除orderdetails你想打印这个? 你可以像下面这个例子那样做。 很容易修改以抛出异常而不是打印或任何你需要的

还为什么要返回声明?

Create Procedure uspDeleteOrder
@orderID int As 

Set nocount on    

declare @DeleteOrderDetailCount int

If Exists (Select * from Orders Where OrderID = @orderID)
Begin
    Begin Try   
        Begin Transaction   
            Delete From dbo.[Order Details]
            Where dbo.[Order Details].OrderID = @orderID    

            select @DeleteOrderDetailCount = @@ROWCOUNT

            Delete From Orders
            Where OrderID = @orderID   

        COMMIT TRANSACTION

        if @DeleteOrderDetailCount = 0
        begin
            Print 'There where no orders details to delete'
        end

        Print 'The Order has been deleted!'

        -- why a return here ????
        -- return
    End Try
    Begin Catch
        IF (@@trancount > 0)
        Begin           
            ROLLBACK TRANSACTION
            RAISERROR ('Error', 16,1); 
        End
        PRINT '*************Error Detail****************'
        PRINT 'Error Number  :' + CAST(ERROR_NUMBER() AS VARCHAR)
        PRINT 'Error Severity:' + CAST(ERROR_SEVERITY() AS VARCHAR)
        PRINT 'Error State   :' + CAST(ERROR_STATE() AS VARCHAR)
        PRINT 'Error Line    :' + CAST(ERROR_LINE() AS VARCHAR)
        PRINT 'Error Message :' + ERROR_MESSAGE()
    End Catch
End
Else 
Begin
    RAISERROR ('No Order ID', 16,1);
End

答案 2 :(得分:0)

您是否尝试过捕获受@@ RowCount影响的行

DECLARE @v1 INT
DELETE From dbo.[Order Details]
Where dbo.[Order Details].OrderID = @orderID    
SET @v1 = @@ROWCOUNT

它允许您实现一些逻辑来捕获不需要的场景。