다음을 통해 공유


Windows Workflow Foundation 예외

워크플로는 TryCatch 작업을 사용하여 워크플로 실행 중에 발생하는 예외를 처리할 수 있습니다. 이러한 예외를 처리하거나 Rethrow 작업을 사용하여 다시 throw할 수 있습니다. Finally 섹션의 활동은 Try 섹션 또는 Catches 섹션이 완료되면 실행됩니다. WorkflowApplication 인스턴스에서 호스트되는 워크플로는 OnUnhandledException 이벤트 처리기를 사용하여 TryCatch 작업에서 처리되지 않는 예외를 처리할 수도 있습니다.

예외의 원인

워크플로에서는 다음과 같은 방법으로 예외를 생성할 수 있습니다.

  • TransactionScope트랜잭션 제한 시간.

  • Throw 작업을 사용하여 워크플로에서 throw된 명시적 예외입니다.

  • 활동에서 throw된 .NET Framework 4.6.1 예외입니다.

  • 워크플로에서 사용되는 라이브러리, 구성 요소 또는 서비스와 같은 외부 코드에서 throw된 예외입니다.

예외 처리

작업에서 예외가 throw되고 처리되지 않은 경우 기본 동작은 워크플로 인스턴스를 종료하는 것입니다. 사용자 지정 OnUnhandledException 처리기가 있는 경우 이 기본 동작을 재정의할 수 있습니다. 이 처리기는 워크플로 호스트 작성자에게 사용자 지정 로깅, 워크플로 중단, 워크플로 취소 또는 워크플로 종료와 같은 적절한 처리를 제공할 수 있는 기회를 제공합니다. 워크플로에서 처리되지 않는 예외가 발생하면 OnUnhandledException 처리기가 호출됩니다. 워크플로의 최종 결과를 결정하는 OnUnhandledException 반환되는 세 가지 가능한 작업이 있습니다.

  • 취소 - 취소된 워크플로 인스턴스는 분기 실행의 정상적인 종료입니다. 취소 동작을 모델링할 수 있습니다(예: CancellationScope 작업 사용). 완료된 처리기는 취소 프로세스가 완료되면 호출됩니다. 취소된 워크플로가 취소됨 상태입니다.

  • 종료 - 종료된 워크플로 인스턴스를 다시 시작하거나 다시 시작할 수 없습니다. 이렇게 하면 종료된 이유로 예외를 제공할 수 있는 Completed 이벤트가 트리거됩니다. 종료 처리기는 종료 프로세스가 완료될 때 호출됩니다. 종료된 워크플로가 오류 상태입니다.

  • 중단 - 중단된 워크플로 인스턴스는 영구로 구성된 경우에만 다시 시작될 수 있습니다. 지속성이 없으면 워크플로를 다시 실행할 수 없습니다. 워크플로가 중단되는 시점에서 마지막 지속성 지점 이후 수행된 모든 작업(메모리)이 손실됩니다. 중단된 워크플로의 경우 중단된 처리기는 중단 프로세스가 완료되는 이유로 예외를 사용하여 호출됩니다. 그러나 Cancelled 및 Terminated와 달리 Completed 처리기는 호출되지 않습니다. 중단된 워크플로가 중단된 상태입니다.

다음 예제에서는 예외를 throw하는 워크플로를 호출합니다. 예외는 워크플로에서 처리되지 않으며 OnUnhandledException 처리기가 호출됩니다. WorkflowApplicationUnhandledExceptionEventArgs 검사하여 예외에 대한 정보를 제공하고 워크플로가 종료됩니다.

Activity wf = new Sequence
{
    Activities =
     {
         new WriteLine
         {
             Text = "Starting the workflow."
         },
         new Throw
        {
            Exception = new InArgument<Exception>((env) =>
                new ApplicationException("Something unexpected happened."))
        },
        new WriteLine
         {
             Text = "Ending the workflow."
         }
     }
};

WorkflowApplication wfApp = new WorkflowApplication(wf);

wfApp.OnUnhandledException = delegate (WorkflowApplicationUnhandledExceptionEventArgs e)
{
    // Display the unhandled exception.
    Console.WriteLine($"OnUnhandledException in Workflow {e.InstanceId}\n{e.UnhandledException.Message}");

    Console.WriteLine($"ExceptionSource: {e.ExceptionSource.DisplayName} - {e.ExceptionSourceInstanceId}");

    // Instruct the runtime to terminate the workflow.
    return UnhandledExceptionAction.Terminate;

    // Other choices are UnhandledExceptionAction.Abort and
    // UnhandledExceptionAction.Cancel
};

wfApp.Run();

TryCatch 작업으로 예외 처리

워크플로 내의 예외 처리는 TryCatch 작업으로 수행됩니다. TryCatch 활동에는 각각 특정 Exception 형식과 연결된 Catch 활동의 Catches 컬렉션이 있습니다. TryCatch 활동의 Try 섹션에 포함된 작업에서 throw된 예외가 Catches 컬렉션의 Catch<TException> 활동 예외와 일치하는 경우 예외가 처리됩니다. 예외가 명시적으로 다시 throw되거나 새 예외가 throw되면 이 예외가 부모 작업으로 전달됩니다. 다음 코드 예제에서는 Throw 활동에 의해 Try 섹션에서 throw되는 ApplicationException 처리하는 TryCatch 활동을 보여 줍니다. 예외의 메시지는 Catch<TException> 활동으로 콘솔에 기록된 다음 Finally 섹션의 콘솔에 메시지가 기록됩니다.

DelegateInArgument<ApplicationException> ex = new DelegateInArgument<ApplicationException>()
{
    Name = "ex"
};

Activity wf = new TryCatch
{
    Try = new Throw()
    {
        Exception = new InArgument<Exception>((env) => new ApplicationException("An ApplicationException was thrown."))
    },
    Catches =
    {
        new Catch<ApplicationException>
        {
            Action = new ActivityAction<ApplicationException>
            {
                Argument = ex,
                Handler = new WriteLine()
                {
                    Text = new InArgument<string>((env) => ex.Get(env).Message)
                }
            }
        }
    },
    Finally = new WriteLine()
    {
        Text = "Executing in Finally."
    }
};

Finally 섹션의 활동은 Try 섹션 또는 Catches 섹션이 성공적으로 완료되면 실행됩니다. 예외가 throw되지 않으면 Try 섹션이 성공적으로 완료되고 예외가 throw되거나 다시 throw되지 않으면 Catches 섹션이 성공적으로 완료됩니다. 예외가 TryCatchTry 섹션에서 throw되고 Catches 섹션의 Catch<TException> 의해 처리되지 않거나 Catches다시 throw되는 경우 다음 중 하나가 발생하지 않는 한 Finally 활동이 실행되지 않습니다.

  • 예외는 해당 상위 수준 TryCatch다시 throw되는지 여부에 관계없이 워크플로의 상위 수준 TryCatch 활동에 의해 catch됩니다.

  • 예외는 더 높은 수준의 TryCatch처리되지 않고 워크플로의 루트를 이스케이프하며 워크플로는 종료 또는 중단 대신 취소하도록 구성됩니다. WorkflowApplication 사용하여 호스트되는 워크플로는 OnUnhandledException 처리하고 Cancel반환하여 이를 구성할 수 있습니다. OnUnhandledException 처리하는 예제는 이 항목의 앞에 나와 있습니다. 워크플로 서비스는 WorkflowUnhandledExceptionBehavior 사용하고 Cancel지정하여 이를 구성할 수 있습니다. WorkflowUnhandledExceptionBehavior구성하는 예제는 워크플로 서비스 호스트 확장성 참조하세요.

예외 처리 및 보정

예외 처리와 보정의 차이점은 작업 실행 중에 예외 처리가 발생한다는 점입니다. 보정은 작업이 성공적으로 완료된 후에 발생합니다. 예외 처리는 작업이 예외를 발생시킨 후 정리할 수 있는 기회를 제공하는 반면, 보정은 이전에 완료된 활동의 성공적으로 완료된 작업을 실행 취소할 수 있는 메커니즘을 제공합니다. 자세한 내용은 보상참조하세요.

참고하십시오