How to serialize a complied workflow definition

Scenario:

OP has a list of complied workflow types, which is created by using reflection to find all types.

            var assembly = Assembly.GetAssembly(this.GetType());

            foreach (Type objType in assembly.GetTypes())
            {
                if (objType.IsSubclassOf(typeof(Activity)))
                {
                    var activity = Activator.CreateInstance(objType) as Activity;
                }
            }

He want to serialize these activities into string, and save it in database. Howeve, when the workflow serialized to Xaml, only a root element of the activity was present.

Cause:

when we instantiate a complied workflow type, the implementation(variables/activities) is invisible.

Resolution:

Inspect the activity tree of the complied type, create an activity by using imperative code, then the instance of this activity is serializable.

static void InspectActivity(Activity root, int indent)
{
    // Inspect the activity tree using WorkflowInspectionServices.
    IEnumerator<Activity> activities = 
        WorkflowInspectionServices.GetActivities(root).GetEnumerator();

    Console.WriteLine("{0}{1}", new string(' ', indent), root.DisplayName);

    while (activities.MoveNext())
    {
        InspectActivity(activities.Current, indent + 2);
    }
}
ActivityBuilder<int> ab = new ActivityBuilder<int>();
ab.Name = "Add";
ab.Properties.Add(new DynamicActivityProperty { Name = "Operand1", Type = typeof(InArgument<int>) });
ab.Properties.Add(new DynamicActivityProperty { Name = "Operand2", Type = typeof(InArgument<int>) });
ab.Implementation = new Sequence
{
    Activities = 
    {
        new WriteLine
        {
            Text = new VisualBasicValue<string>("Operand1.ToString() + \" + \" + Operand2.ToString()")
        },
        new Assign<int>
        {
            To = new ArgumentReference<int> { ArgumentName = "Result" },
            Value = new VisualBasicValue<int>("Operand1 + Operand2")
        }
    }
};
// Serialize the workflow to XAML and store it in a string.
StringBuilder sb = new StringBuilder();
StringWriter tw = new StringWriter(sb);
XamlWriter xw = ActivityXamlServices.CreateBuilderWriter(new XamlXmlWriter(tw, new XamlSchemaContext()));
XamlServices.Save(xw , ab);
string serializedAB = sb.ToString();

// Display the XAML to the console.
Console.WriteLine(serializedAB);

// Serialize the workflow to XAML and save it to a file.
StreamWriter sw = File.CreateText(@"C:\Workflows\add.xaml");
XamlWriter xw2 = ActivityXamlServices.CreateBuilderWriter(new XamlXmlWriter(sw, new XamlSchemaContext()));
XamlServices.Save(xw2, ab);
sw.Close();

Serializing Workflows and Activities to and from XAML

http://msdn.microsoft.com/en-us/library/ff458319

Authoring Workflows, Activities, and Expressions Using Imperative Code

http://msdn.microsoft.com/en-us/library/ee358749

posted @ 2012-06-22 11:28  Leo Tang  阅读(370)  评论(0)    收藏  举报