如何检查处理事件时是否发生异常(.Net)

How to check if exception occured on disposing an event (.Net)

处理对象时,我想检查是否发生异常以选择是​​否执行 COMMIT。我正在使用针对 SAP 的 BAPI。

如果创建运输单(1)失败,我想取消material单据(2)。 (但这不属于问题)

          Dim rfcFunction As IRfcFunction

    Try

        Using sapConn3 As New SapConnectorV3
          ' (1) Creation of a Transport-Order
        End Using

    Catch ex As Exception

        Using sapConn3 As New SapConnectorV3
          ' (2) Cancel MaterialDocument
          ' (EDIT) The problem can be fixed if I call 
          ' "CommitTransaction" manually at this line. But I want to do 
          ' this automatically on disposing the object
        End Using

        Throw

    End Try

当 Using-Block 结束时,对象被释放,此时我必须知道是否发生了异常。

这个函数不起作用,因为它在两个处理中都声明为真:

 Protected ReadOnly Property ExceptionOccurred() As Boolean
    Get
        Return Runtime.InteropServices.Marshal.GetExceptionCode <> 0
    End Get
End Property

这就是我决定是否提交的方式(部分 Dispose():

 Public Sub Dispose() Implements IDisposable.Dispose

     If Not ExceptionOccurred Then

        CommitTransaction()

    End If

我认为你有 Try Catch 和你使用错误的方法。我认为你需要的模式如下:

Using sapConn3 As New SapConnectorV3
    Try   
      StartTransaction       
      ' (1) Creation of a Transport-Order
      CommitTransaction
    Catch ex As Exception
      ' (2) Cancel MaterialDocument
      RollbackTransaction
    End Try
End Using

检测异常的发生很简单,你把代码放在Catch块中来检测这个

"it is disposed because an exception is occured" - 对象没有被释放因为发生了异常,所以无法在对象本身内部检测到这一点。考虑这些:

    Using sapConn3 As New SapConnectorV3
        Try
            'do something
        Catch ex As Exception
            'exception is thrown but object is not yet disposed
        End Try
    End Using 'object is now disposed


    Try
        Using sapConn3 As New SapConnectorV3
            'do somework
        End Using 'object is disposed here
    Catch ex As Exception
        'object must have be dispoed at this point as we are outide the using block
    End Try

所以通过使用第一个选项,您不需要检查对象本身内部

你可以从相反的方向解决这个问题。不要试图在发生故障时通知您的 SapConnectionV3 对象,而是在您 成功 .

时告诉它

您只需添加一个 Complete()CompletedSuccessfully() 或类似的方法到您的 SapConnectorV3,这将设置一个私有的 bool 标志。在您离开 Using 块之前调用它。然后,在您的 Dispose 实现中,如果标志为真则提交,如果为假则回滚。

然后你的调用约定变成:

Using sapConn3 As New SapConnectorV3
    ' Do some work.
    sapConn3.Complete()
End Using ' Now this will commit if Complete was called, or roll back otherwise.