You've already forked linux-packaging-mono
Imported Upstream version 4.0.0~alpha1
Former-commit-id: 806294f5ded97629b74c85c09952f2a74fe182d9
This commit is contained in:
382
external/referencesource/System.Workflow.Activities/StateValidator.cs
vendored
Normal file
382
external/referencesource/System.Workflow.Activities/StateValidator.cs
vendored
Normal file
@ -0,0 +1,382 @@
|
||||
namespace System.Workflow.Activities
|
||||
{
|
||||
#region Imports
|
||||
|
||||
using System;
|
||||
using System.Text;
|
||||
using System.Reflection;
|
||||
using System.Collections;
|
||||
using System.CodeDom;
|
||||
using System.ComponentModel;
|
||||
using System.ComponentModel.Design;
|
||||
using System.Drawing.Design;
|
||||
using System.Drawing;
|
||||
using System.Diagnostics;
|
||||
using System.Workflow.ComponentModel;
|
||||
using System.Workflow.ComponentModel.Design;
|
||||
using System.Runtime.Serialization;
|
||||
using System.Collections.Generic;
|
||||
using System.ComponentModel.Design.Serialization;
|
||||
using System.Xml.Serialization;
|
||||
using System.Workflow.ComponentModel.Compiler;
|
||||
using System.Workflow.Activities.Common;
|
||||
|
||||
#endregion
|
||||
|
||||
#region StateValidator class
|
||||
|
||||
[System.Runtime.InteropServices.ComVisible(false)]
|
||||
[Obsolete("The System.Workflow.* types are deprecated. Instead, please use the new types from System.Activities.*")]
|
||||
public class StateActivityValidator : CompositeActivityValidator
|
||||
{
|
||||
public override ValidationErrorCollection Validate(ValidationManager manager, object obj)
|
||||
{
|
||||
ValidationErrorCollection validationErrors = new ValidationErrorCollection(base.Validate(manager, obj));
|
||||
|
||||
StateActivity state = obj as StateActivity;
|
||||
if (state == null)
|
||||
throw new ArgumentException(SR.GetString(SR.Error_UnexpectedArgumentType, typeof(StateActivity).FullName), "obj");
|
||||
|
||||
// First we validate contaiment
|
||||
if (state.Parent != null)
|
||||
{
|
||||
if (StateMachineHelpers.IsStateMachine(state))
|
||||
{
|
||||
validationErrors.Add(new ValidationError(SR.GetError_StateMachineWorkflowMustBeARootActivity(), ErrorNumbers.Error_StateMachineWorkflowMustBeARootActivity));
|
||||
return validationErrors;
|
||||
}
|
||||
else
|
||||
{
|
||||
// Make sure that a State is always contained in
|
||||
// another State or StateMachineWorkflow. State machine
|
||||
// within a sequential workflow is not supported
|
||||
if (!(state.Parent is StateActivity))
|
||||
{
|
||||
validationErrors.Add(new ValidationError(SR.GetError_InvalidStateActivityParent(), ErrorNumbers.Error_InvalidStateActivityParent));
|
||||
return validationErrors;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (state.Parent == null && !StateMachineHelpers.IsStateMachine(state))
|
||||
{
|
||||
ValidateCustomStateActivity(state, validationErrors);
|
||||
}
|
||||
|
||||
if (StateMachineHelpers.IsLeafState(state))
|
||||
{
|
||||
ValidateLeafState(state, validationErrors);
|
||||
}
|
||||
else if (StateMachineHelpers.IsRootState(state))
|
||||
{
|
||||
ValidateRootState(state, validationErrors);
|
||||
}
|
||||
else
|
||||
{
|
||||
ValidateState(state, validationErrors);
|
||||
}
|
||||
|
||||
ValidateEventDrivenActivities(state, validationErrors);
|
||||
|
||||
return validationErrors;
|
||||
}
|
||||
|
||||
private static void ValidateCustomStateActivity(StateActivity state, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
if (state.Activities.Count > 0)
|
||||
{
|
||||
validationErrors.Add(new ValidationError(SR.GetError_BlackBoxCustomStateNotSupported(), ErrorNumbers.Error_BlackBoxCustomStateNotSupported));
|
||||
}
|
||||
}
|
||||
|
||||
public override ValidationError ValidateActivityChange(Activity activity, ActivityChangeAction action)
|
||||
{
|
||||
if (activity == null)
|
||||
throw new ArgumentNullException("activity");
|
||||
if (action == null)
|
||||
throw new ArgumentNullException("action");
|
||||
|
||||
if (activity.ExecutionStatus != ActivityExecutionStatus.Initialized &&
|
||||
activity.ExecutionStatus != ActivityExecutionStatus.Executing &&
|
||||
activity.ExecutionStatus != ActivityExecutionStatus.Closed)
|
||||
{
|
||||
return new ValidationError(SR.GetString(SR.Error_DynamicActivity2, activity.QualifiedName, activity.ExecutionStatus, activity.GetType().FullName), ErrorNumbers.Error_DynamicActivity2);
|
||||
}
|
||||
|
||||
RemovedActivityAction remove = action as RemovedActivityAction;
|
||||
if (remove != null)
|
||||
{
|
||||
StateActivity removedState = remove.OriginalRemovedActivity as StateActivity;
|
||||
if (removedState != null)
|
||||
{
|
||||
// we don't have a way to check if the removed
|
||||
// activity is executing or not, so if the user is trying to
|
||||
// remove a StateActivity, we simply disallow it.
|
||||
//
|
||||
|
||||
return new ValidationError(
|
||||
SR.GetError_CantRemoveState(removedState.QualifiedName),
|
||||
ErrorNumbers.Error_CantRemoveState);
|
||||
}
|
||||
|
||||
if (activity.ExecutionStatus == ActivityExecutionStatus.Executing)
|
||||
{
|
||||
EventDrivenActivity removedEventDriven = remove.OriginalRemovedActivity as EventDrivenActivity;
|
||||
if (removedEventDriven != null)
|
||||
{
|
||||
return new ValidationError(
|
||||
SR.GetError_CantRemoveEventDrivenFromExecutingState(removedEventDriven.QualifiedName, activity.QualifiedName),
|
||||
ErrorNumbers.Error_CantRemoveEventDrivenFromExecutingState);
|
||||
}
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="state"></param>
|
||||
/// <returns></returns>
|
||||
private static void ValidateLeafState(StateActivity state, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
ValidateLeafStateChildren(state, validationErrors);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="state"></param>
|
||||
/// <returns></returns>
|
||||
private static void ValidateRootState(StateActivity state, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
ValidateCompositeStateChildren(state, validationErrors);
|
||||
if (StateMachineHelpers.IsStateMachine(state))
|
||||
{
|
||||
ValidateInitialState(state, validationErrors);
|
||||
ValidateCompletedState(state, validationErrors);
|
||||
}
|
||||
}
|
||||
|
||||
private static void ValidateState(StateActivity state, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
ValidateCompositeStateChildren(state, validationErrors);
|
||||
}
|
||||
|
||||
#region Helpers
|
||||
|
||||
private static void ValidateLeafStateChildren(StateActivity state, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
bool invalidChild = false;
|
||||
|
||||
foreach (Activity activity in state.Activities)
|
||||
{
|
||||
if (!activity.Enabled)
|
||||
continue;
|
||||
|
||||
if (activity is EventDrivenActivity ||
|
||||
activity is StateInitializationActivity ||
|
||||
activity is StateFinalizationActivity)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
invalidChild = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// validate that all child activities are event driven activities.
|
||||
if (invalidChild)
|
||||
validationErrors.Add(new ValidationError(
|
||||
SR.GetError_InvalidLeafStateChild(),
|
||||
ErrorNumbers.Error_InvalidLeafStateChild));
|
||||
}
|
||||
|
||||
private static void ValidateCompositeStateChildren(StateActivity state, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
bool invalidChild = false;
|
||||
|
||||
foreach (Activity activity in state.Activities)
|
||||
{
|
||||
if (!activity.Enabled)
|
||||
continue;
|
||||
|
||||
if (activity is EventDrivenActivity ||
|
||||
activity is StateActivity)
|
||||
{
|
||||
continue;
|
||||
}
|
||||
else
|
||||
{
|
||||
invalidChild = true;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (invalidChild)
|
||||
validationErrors.Add(new ValidationError(
|
||||
SR.GetError_InvalidCompositeStateChild(),
|
||||
ErrorNumbers.Error_InvalidCompositeStateChild));
|
||||
}
|
||||
|
||||
private static void ValidateInitialState(StateActivity state, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
string initialStateName = StateMachineHelpers.GetInitialStateName(state);
|
||||
if (String.IsNullOrEmpty(initialStateName))
|
||||
{
|
||||
if (state.Activities.Count > 0)
|
||||
{
|
||||
// we only require an initial state if the state machine is
|
||||
// not empty
|
||||
validationErrors.Add(new ValidationError(
|
||||
SR.GetString(SR.Error_PropertyNotSet, StateMachineWorkflowActivity.InitialStateNamePropertyName),
|
||||
ErrorNumbers.Error_PropertyNotSet, false,
|
||||
StateMachineWorkflowActivity.InitialStateNamePropertyName));
|
||||
}
|
||||
}
|
||||
else
|
||||
{
|
||||
StateActivity initialState = StateMachineHelpers.FindStateByName(
|
||||
state,
|
||||
initialStateName);
|
||||
if (initialState == null)
|
||||
{
|
||||
validationErrors.Add(new ValidationError(
|
||||
SR.GetError_InitialStateMustPointToAState(),
|
||||
ErrorNumbers.Error_InitialStateMustPointToAState,
|
||||
false,
|
||||
StateMachineWorkflowActivity.InitialStateNamePropertyName));
|
||||
}
|
||||
else
|
||||
{
|
||||
if (!StateMachineHelpers.IsLeafState(initialState))
|
||||
{
|
||||
validationErrors.Add(new ValidationError(
|
||||
SR.GetError_InitialStateMustPointToALeafNodeState(),
|
||||
ErrorNumbers.Error_InitialStateMustPointToALeafNodeState,
|
||||
false,
|
||||
StateMachineWorkflowActivity.InitialStateNamePropertyName));
|
||||
}
|
||||
|
||||
// InitialState cannot be the completed state
|
||||
string completedStateName = StateMachineHelpers.GetCompletedStateName(state);
|
||||
if (initialStateName == completedStateName)
|
||||
{
|
||||
validationErrors.Add(new ValidationError(
|
||||
SR.GetError_InitialStateMustBeDifferentThanCompletedState(),
|
||||
ErrorNumbers.Error_InitialStateMustBeDifferentThanCompletedState,
|
||||
false,
|
||||
StateMachineWorkflowActivity.InitialStateNamePropertyName));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static void ValidateCompletedState(StateActivity state, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
string completedStateName = StateMachineHelpers.GetCompletedStateName(state);
|
||||
if (!String.IsNullOrEmpty(completedStateName))
|
||||
{
|
||||
StateActivity completedState = StateMachineHelpers.FindStateByName(
|
||||
state,
|
||||
completedStateName);
|
||||
if (completedState == null)
|
||||
{
|
||||
validationErrors.Add(new ValidationError(
|
||||
SR.GetError_CompletedStateMustPointToAState(),
|
||||
ErrorNumbers.Error_CompletedStateMustPointToAState,
|
||||
false,
|
||||
StateMachineWorkflowActivity.CompletedStateNamePropertyName));
|
||||
}
|
||||
else
|
||||
{
|
||||
if (StateMachineHelpers.IsLeafState(completedState))
|
||||
{
|
||||
if (completedState.EnabledActivities.Count > 0)
|
||||
validationErrors.Add(new ValidationError(
|
||||
SR.GetString(SR.Error_CompletedStateCannotContainActivities),
|
||||
ErrorNumbers.Error_CompletedStateCannotContainActivities,
|
||||
false,
|
||||
StateMachineWorkflowActivity.CompletedStateNamePropertyName));
|
||||
}
|
||||
else
|
||||
{
|
||||
validationErrors.Add(new ValidationError(
|
||||
SR.GetError_CompletedStateMustPointToALeafNodeState(),
|
||||
ErrorNumbers.Error_CompletedStateMustPointToALeafNodeState,
|
||||
false,
|
||||
StateMachineWorkflowActivity.CompletedStateNamePropertyName));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
private static void ValidateEventDrivenActivities(StateActivity state, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
List<EventDrivenActivity> eventDrivenList = new List<EventDrivenActivity>();
|
||||
|
||||
foreach (Activity activity in state.EnabledActivities)
|
||||
{
|
||||
EventDrivenActivity eventDriven = activity as EventDrivenActivity;
|
||||
if (eventDriven != null)
|
||||
{
|
||||
eventDrivenList.Add(eventDriven);
|
||||
}
|
||||
}
|
||||
foreach (EventDrivenActivity eventDriven in eventDrivenList)
|
||||
{
|
||||
bool result = ValidateMultipleIEventActivity(eventDriven, validationErrors);
|
||||
if (!result)
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private static bool ValidateMultipleIEventActivity(EventDrivenActivity eventDriven, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
IEventActivity firstEventActivity = null;
|
||||
if (eventDriven.EnabledActivities.Count > 0)
|
||||
{
|
||||
firstEventActivity = eventDriven.EnabledActivities[0] as IEventActivity;
|
||||
}
|
||||
|
||||
return ValidateMultipleIEventActivityInCompositeActivity(eventDriven, firstEventActivity, eventDriven, validationErrors);
|
||||
}
|
||||
|
||||
private static bool ValidateMultipleIEventActivityInCompositeActivity(EventDrivenActivity eventDriven, IEventActivity firstEventActivity, CompositeActivity parent, ValidationErrorCollection validationErrors)
|
||||
{
|
||||
foreach (Activity activity in parent.Activities)
|
||||
{
|
||||
// Skip disabled activities or the first IEventActivity
|
||||
// Note that we don't use EnabledActivities because we want to
|
||||
// enforce this rule inside Cancellation and Exception Handlers.
|
||||
if (!activity.Enabled || activity == firstEventActivity)
|
||||
continue;
|
||||
|
||||
if (activity is IEventActivity)
|
||||
{
|
||||
validationErrors.Add(new ValidationError(
|
||||
SR.GetString(SR.Error_EventDrivenMultipleEventActivity, eventDriven.Name, typeof(IEventActivity).FullName, typeof(EventDrivenActivity).Name),
|
||||
ErrorNumbers.Error_EventDrivenMultipleEventActivity));
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
CompositeActivity compositeActivity = activity as CompositeActivity;
|
||||
if (compositeActivity != null)
|
||||
{
|
||||
bool result = ValidateMultipleIEventActivityInCompositeActivity(eventDriven, firstEventActivity, compositeActivity, validationErrors);
|
||||
if (!result)
|
||||
return false;
|
||||
}
|
||||
}
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
#endregion
|
||||
}
|
||||
|
||||
#endregion StateValidator class
|
||||
}
|
Reference in New Issue
Block a user