Thursday, 21 January 2010

First steps with WF4 in VS2010 Beta 2

Here are some useful links:

http://msdn.microsoft.com/en-us/netframework/wf-webcasts.aspx
http://channel9.msdn.com/posts/mwink/Rules-Driven-UI-using-WF/

http://msdn.microsoft.com/en-us/library/ee342461.aspx

There are a series of good webcasts at:
http://bloggersguides.net/

Getting started
http://msdn.microsoft.com/en-us/library/dd489454(VS.100).aspx

http://msdn.microsoft.com/en-gb/netframework/first-steps-with-wf.aspx
http://blogs.msdn.com/mwinkle

Here is how to create a hallo world WF4 Console Application.
1. Create a New "WorkFlow Console Application
2. Modify Program.cs to

using System;
using System.Linq;
using System.Activities;
using System.Activities.Statements;

namespace WorkflowConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            WorkflowInvoker.Invoke(new Workflow1());
            Console.WriteLine("Hit to quit");
            Console.ReadLine();
        }
    }
}

3. Add a new project of type Activity Library
4. Add a reference from the console application to the Activity library project
5. Add a new Code Activity to the Activity libray

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Activities;

namespace ActivityLibrary1
{

    public sealed class NigelRead : CodeActivity
    {
        // Define an activity input argument of type string
        public OutArgument<string> Text { get; set; }

        // If your activity returns a value, derive from CodeActivity<TResult>
        // and return the value from the Execute method.
        protected override void Execute(CodeActivityContext context)
        {
            // Obtain the runtime value of the Text input argument
            String t = Console.ReadLine();
            Text.Set(context, t);
        }
    }
}

6. Add anothe Code Activity
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Activities;

namespace ActivityLibrary1
{

    public sealed class NigelWriteLine : CodeActivity
    {
        public InArgument<string> Text { get; set; }
        protected override void Execute(CodeActivityContext context)
        {
            string test2 = Text.Get<String>(context);
            Console.WriteLine(">" + test2);

        }
    }
}

7. Add a new Activity
8. Rebuild the solution
9. Add a FlowChart
10. Drag and drop 1 NigelWriteLine 1 NigelReadLine and 1 NigelWriteLine into the flow chart
11. Join the three activities together under the green start circle
12. Click the Variables tab and Add MyName as a string with a defaul vbalue "Unknown"
13. In the Text field of of the first NigelWriteLine set "What is your name?"
14. In the Text field of NigelReadLine set MyName
15. In the Text field of NigelWriteLine set MyName
16. Rebuild the solution
17. In the Workflow1.xaml file drag and drop the activity just created
18. Run the Application

The result will be
>What is your name
Nigel
>Nigel
Hit to quit

Since the work flow is an object stack, here is an alternative way of executing the workflow:

Sequence wf = new Sequence
{
    Activities = {
        new CodeActivity1{Text="Hallo World"}
    }
};
WorkflowInvoker.Invoke(wf);
MessageBox.Show("WorkFLow Complete");

If you have have a long running task then derive from AsyncCodeActivity or CodeActivity<T>
Then you have to implement BeginExecute and EndExecute

There is an example showing how persistance works here http://stackoverflow.com/questions/2021433/windows-workflow-foundation-4-0-and-persistence

The database scripts are found in C:\WINDOWS\Microsoft.NET\Framework\v4.0.21006\SQL\en

SqlPersistenceService_Schema.sql
SqlPersistenceService_Logic.sql

It should work by creating a SqlWorkflowInstanceStore. Unfortunately on my version of the Beta of VS2010 I could not resolve this.