How to: Publish and Run a Workflow for Workflow Manager 1.0

 

Updated: May 15, 2013

In this step of the Getting Started Tutorial, a workflow client application is created that creates a scope, publishes the activity and workflow, and then invokes the workflow. This step also demonstrates the Workflow Resource Browser sample.

Note

To watch a video walkthrough, or download the starter files and a completed version of the tutorial, including the Workflow Resource Browser sample, see Workflow Manager 1.0 - Getting Started Tutorial.

In this Tutorial Step

  • Add the Microsoft.Workflow.Samples.Common project

  • Create the Workflow Client Application

  • Run the Workflow Client Application

  • Run the Workflow Resource Browser

  • Troubleshooting Steps

Add the Microsoft.Workflow.Samples.Common project

The Microsoft.Workflow.Samples.Common project contains helper classes and extension methods that simplify the administration of workflow manager projects, including publishing scopes, activities, and workflows, and is added to the solution in this step.

  1. Download and extract the starter files for the tutorial from Workflow Manager 1.0 - Getting Started Tutorial.

  2. Open the solution from the previous step in the tutorial, How to: Create a Custom Activity, if it is not already open in Visual Studio 2012.

  3. Right-click WFMgrGettingStarted in Solution Explorer and choose Add, Existing Project.

  4. Browse to the location where you extracted the starter files for the tutorial, and navigate to the following folder.

    <Starter files location>\Start\Microsoft.Workflow.Samples.Common

  5. Select Microsoft.Workflow.Samples.Common.csproj and click Open.

  6. Press Ctrl+Shift+B to build the solution.

Create the Workflow Client Application

The workflow client application is created in this step. The workflow client application creates a scope, publishes the activity and workflow to the scope, and then invokes the workflow. As the workflow is running, the client application polls for status updates and displays the status containing the products retrieved by the search. After the application completes, the scope is cleaned up and the workflow artifacts are removed.

  1. Right-click WFMgrGettingStarted in Solution Explorer and choose Add, New Project.

  2. In the Installed node, select Visual C#, Windows. Ensure that .NET Framework 4.5 is selected in the .NET Framework version drop-down list. Select Console Application from the list. Type GetProductsWorkflowClient in the Name box and then click OK.

  3. Right-click GetProductsWorkflowClient in Solution Explorer and select Add Reference.

  4. Select Solution from the Add Reference list, and check the boxes beside Microsoft.Workflow.Samples.Common and GetProductsActivities.

  5. Click the Browse button and navigate to C:\Program Files\Reference Assemblies\Microsoft\Workflow Manager\1.0.

  6. Select Microsoft.Workflow.Client.dll and Microsoft.Activities.dll, and click Add.

  7. Click OK to dismiss the Reference Manager window and add the references.

  8. Double-click Program.cs in Solution Explorer to display the code.

  9. Add the following using statements at the top of the file with the other using statements (Snippet3).

    using Microsoft.Workflow.Client;  
    using Microsoft.Workflow.Samples.Common;  
    

    Tip

    Snippet files are provided for the tutorial. To use them, download the starter files for the tutorial from Workflow Manager 1.0 - Getting Started Tutorial. In Visual Studio, choose Code Snippets Manager from the Tools menu. Select Visual C# from the Language drop-down, and then click the Add button. Browse to the location where you extracted the starter files and select the Assets\WFMgrGettingStarted folder. Click Select Folder, and then click OK. In your code file, right-click at the point at which you wish to insert the snippet, and select Insert Snippet. Scroll down the list and double-click WFMgrGettingStarted, and then double-click the desired snippet.

  10. Add the following two static member variables to the Program class (Snippet4).

    static string workflowName = "GetProductsWorkflow";  
    static string baseAddress = "https://<Base address>:12290/";  
    

    Important

    The baseAddress must point to the Workflow Manager server. If you are hosting the Workflow Manager server on your development machine, you can get this name by inspecting the computer name. To find the machine name click Start, right-click Computer, and view the full computer name. Configure the baseAddress with the full computer name in the following manner: https://Full computer name:12290, for example https://mycomputername:12290/ or https://myserver.mydomain.mycompany.com:12290/.

  11. Add the following lines of code to the Main method (Snippet5).

    Console.Write("Setting up scope...");  
    WorkflowManagementClient client = WorkflowUtils.CreateForSample(baseAddress, "WFMgrGettingStarted");  
    WorkflowUtils.PrintDone();  
    
    Console.Write("Publishing GetProducts activity...");  
    client.PublishActivity("GetProducts", @"..\..\..\GetProductsActivities\GetProducts.xaml");  
    WorkflowUtils.PrintDone();  
    
    Console.Write("Publishing Workflow...");  
    client.PublishWorkflow(workflowName, @"..\..\..\GetProductsActivities\GetProductsWorkflow.xaml");  
    WorkflowUtils.PrintDone();  
    

    This code uses extension methods and helper classes defined in the Microsoft.Workflow.Samples.Common project to simplify the tasks of publishing scopes, activities, and workflows, and managing them. The code in this step creates a scope, and uses the returned WorkflowManagementClient instance to publish GetProducts and GetProductsWorkflow to the scope.

  12. Add the following lines of code to the Main method so that they follow the previous lines of code. This code prompts the user for the search term to use when querying the Northwind oData service (Snippet6).

    Console.Write("Enter a search keyword: ");  
    string SearchKeyword = Console.ReadLine();  
    
  13. Start the workflow instance by adding the following lines of code after the code from the previous step (Snippet7).

    Console.Write("Starting workflow instance...");  
    WorkflowStartParameters startParameters = new WorkflowStartParameters();  
    startParameters.Content.Add("SearchKeyword", SearchKeyword);  
    string instanceId = client.Workflows.Start(workflowName, startParameters);  
    WorkflowUtils.PrintDone();  
    

    This code assembles the start parameters for the workflow, which map to the In arguments of the workflow, and uses them to start an instance of the workflow.

  14. Add the following code to Main so that it follows the code from the previous step (Snippet8).

    Console.WriteLine("\nPolling UserStatus...\n");  
    string finalUserStatus = client.WaitForWorkflowCompletion(workflowName, instanceId);  
    WorkflowUtils.Print("Completed with status: " + finalUserStatus, ConsoleColor.Green);  
    

    This code uses the WaitForWorkflowCompletion extension method defined in the Microsoft.Workflow.Samples.Common project to wait for the workflow to complete, and poll for status updates set by the SetStatus activity while it is waiting.

  15. Add the following code to the end of Main so that it follows the code from the previous steps (Snippet9).

    Console.WriteLine("Press any key to clean up scope.");  
    Console.ReadKey();  
    
    client.CleanUp();  
    
    Console.WriteLine("Press any key to exit.");  
    Console.ReadKey();  
    

    When the scope is cleaned up the workflow artifacts are removed and then the scope is removed. In a production scenario these tasks would typically done by an administrator, but for the purposes of this sample they are done in code.

    The following example contains the complete Program class (Snippet10).

    class Program  
    {  
        static string workflowName = "GetProductsWorkflow";  
        static string baseAddress = "https:<Base address>:12290/";  
    
        static void Main(string[] args)  
        {  
            Console.Write("Setting up scope...");  
            WorkflowManagementClient client = WorkflowUtils.CreateForSample(baseAddress, "WFMgrGettingStarted");  
            WorkflowUtils.PrintDone();  
    
            Console.Write("Publishing GetProducts activity...");  
            client.PublishActivity("GetProducts", @"..\..\..\GetProductsActivities\GetProducts.xaml");  
            WorkflowUtils.PrintDone();  
    
            Console.Write("Publishing Workflow...");  
            client.PublishWorkflow(workflowName, @"..\..\..\GetProductsActivities\GetProductsWorkflow.xaml");  
            WorkflowUtils.PrintDone();  
    
            Console.Write("Enter a search keyword: ");  
            string SearchKeyword = Console.ReadLine();  
    
            Console.Write("Starting workflow instance...");  
            WorkflowStartParameters startParameters = new WorkflowStartParameters();  
            startParameters.Content.Add("SearchKeyword", SearchKeyword);  
            string instanceId = client.Workflows.Start(workflowName, startParameters);  
            WorkflowUtils.PrintDone();  
    
            Console.WriteLine("\nPolling UserStatus...\n");  
            string finalUserStatus = client.WaitForWorkflowCompletion(workflowName, instanceId);  
            WorkflowUtils.Print("Completed with status: " + finalUserStatus, ConsoleColor.Green);  
    
            Console.WriteLine("Press any key to clean up scope.");  
            Console.ReadKey();  
    
            client.CleanUp();  
    
            Console.WriteLine("Press any key to exit.");  
            Console.ReadKey();  
        }  
    }  
    

Run the Workflow Client Application

System_CAPS_ICON_important.jpg Important

The steps in this section require Visual Studio to be run in administrative mode. If Visual Studio was not started in administrative mode, close Visual Studio, restart it administrative mode, and re-open the solution.

  1. Right-click GetProductsWorkflowClient in Solution Explorer and select Set as StartUp Project.

  2. Press Ctrl+F5 to start the application.

    Tip

    If there are any issues when running the sample, see Troubleshooting Steps for solutions to common issues.

  3. Once the scope is set up, and the GetProducts activity and GetProductsWorkflow are published, type a search term such as choc when prompted and press ENTER. This search term will be used to query for products in the Northwind sample database. To return the first 20 products in the database (the maximum that is returned by this sample), press ENTER without entering a search term.

    The GetProducts activity queries the Northwind oData service hosted at http://services.odata.org/Northwind/Northwind.svc and returns a DynamicValue containing the products that match the search keyword. The GetProductsWorkflow then iterates through them and specifies them as user status updates using the SetUserStatus activity. The client application polls for these status updates and displays the products. After the application completes, the user is prompted to press any key to clean up the scope.

  4. Press any key to clean up the scope, and then press any key to exit.

  5. Press CTRL+F5 to run the application again and try different search terms.

    To see a video walkthrough of this tutorial step, see Workflow Manager 1.0 - Getting Started Tutorial

Run the Workflow Resource Browser

In this task the Workflow Resource Browser sample is used to browse the scope and workflow artifacts created by the workflow client application. The Workflow Resource Browser can be downloaded separately, but it is also included in the starter files for the tutorial that were downloaded in the Add the Microsoft.Workflow.Samples.Common project section.

  1. Open a new instance of Visual Studio 2012, and choose Open, Project/Solution from the File menu.

    Important

    Do not close the WFMgrGettingStarted solution as it is used in this step along with the Workflow Resource Browser sample.

  2. Browse to the location where you extracted the starter files for the tutorial, and navigate to the following folder.

    <Starter files location>\Workflow Resource Browser Tool

  3. Select WFExplorer.sln and click Open.

  4. Press Ctrl+F5 to build and run the application

  5. If prompted for a Workflow Service Address, and the correct address is not pre-populated in the box, use the base address that you used when running the tutorial, and click Connect.

  6. Note that there are no child scopes. Switch back to the previous Visual Studio instance and run the GetProductsWorkflowClient application again. Enter a search term, but when the workflow completes do not press any key to clean up the scope.

  7. Switch back the Workflow Explorer window and press F5 to refresh the view.

  8. Note that the WFMgrGettingStarted scope is present. Click WFMgrGettingStarted to select it, and note that it has two activities and one workflow. This is because both the GetProducts activity and the GetProductsWorkflow are activities, but only GetProductsWorkflow was published as a workflow.

  9. Click the various elements in the right-hand pane to explore the items in the scope, and use the back button at the top of the pane to return to the default view for the scope.

  10. Switch back the GetProductsWorkflowClient console window and press any key to clean up the scope, and then switch back to the Workflow Explorer window, press F5 to refresh, and note that the scope is removed.

Troubleshooting Steps

The steps in this section can be used to resolve common issues when developing Workflow Manager applications.

  • Workflow client application freezes or timeout exceptions are thrown

  • System.Net.WebException: The underlying connection was closed: Could not establish trust relationship for the SSL/TLS secure channel

  • System.UnauthorizedAccessException: The caller does not have the necessary permissions required for this operation. Permissions granted: None. Required permissions: WriteScope

  • System.Xaml.XamlObjectWriterException: Cannot create unknown type '{clr-namespace:GetProductsActivities}GetProducts'.

  • Activity could not be loaded because of errors in the XAML.

  • Could not find type 'DynamicValue' in namespace 'https://schemas.microsoft.com/workflow/2012/xaml/activities'.

Workflow client application freezes or timeout exceptions are thrown

Ensure the following services are started and then try the application again.

  • Service Bus Gateway

  • Service Bus Message Broker

  • SQL Server (SQLEXPRESS or your server)

  • Workflow Manager Backend

Make sure that the computer has internet access. The sample queries the Northwind odata service hosted at http://services.odata.org/Northwind/Northwind.svc, and if the machine doesn't have internet access the sample will not work properly. On virtual machines this issue can sometimes be resolved by clicking the network icon in the system tray and clicking Troubleshoot problems. Once internet access is restored, try the sample again.

Make sure that the baseAddress references the Workflow Manager server. If the Workflow Manager server is hosted on the current machine, click Start, right-click Computer, view the full computer name, and configure the baseAddress with the full computer name in the following manner: https://Full computer name:12290, for example https://mycomputer:12290/ or https://myserver.mydomain.mycompany.com:12290/.

If these issues continue to occur, it is possible that the scope is corrupted. This could possibly occur if the sample is stopped during its execution and the scope is not completely set up or cleaned up. If the services are running and the base address is correct, but issues continue to occur, you can try changing the scope name in the sample to a different name, such as WFMgrGettingStarted2, as shown in the following example.

WorkflowManagementClient client = WorkflowUtils.CreateForSample(baseAddress, "WFMgrGettingStarted2");  

System.Net.WebException: The underlying connection was closed: Could not establish trust relationship for the SSL/TLS secure channel

This issue can occur if there is a mismatch between the base address and the address used for the certificate in IIS, or if there is no SSL certificate configured (which may be the case on local development machines). To resolve, make sure the base address matches the address on the certificate, or you can add the following code in your application so that it is invoked before the workflow manager is accessed for the first time.

// The following code allows a client to use a non-fully qualified name and resolves https issues such as:  
// System.Net.WebException: The underlying connection was closed: Could not establish trust   
// relationship for the SSL/TLS secure channel  
// NOT for production, only for limited local development.  
System.Net.ServicePointManager.ServerCertificateValidationCallback += delegate(object sender,  
            System.Security.Cryptography.X509Certificates.X509Certificate certificate,  
            System.Security.Cryptography.X509Certificates.X509Chain chain,  
            System.Net.Security.SslPolicyErrors sslPolicyErrors)  
{  
    return true;  
};  

System.UnauthorizedAccessException: The caller does not have the necessary permissions required for this operation. Permissions granted: None. Required permissions: WriteScope

This exception can occur if Visual Studio is not started using administrative privileges and the sample is run from within Visual Studio. To resolve, start Visual Studio in administrative mode.

System.Xaml.XamlObjectWriterException: Cannot create unknown type '{clr-namespace:GetProductsActivities}GetProducts'.

If this error occurs when you publish a workflow that references a previously published activity, check the following items.

Open the Assembly.cs of the project that contains the custom activity and verify that the following line is there:

[assembly: XmlnsDefinition("wf://workflow.windows.net/$Current/$Activities", "GetProductsActivities")]  

The second parameter must match the namespace of the project that contains the custom activities. If this line is not present, add it, and add a using System.Windows.Markup; at the top of the file. Build the custom activity project again, and then delete and re-add the activity into the workflow. Once the activity is a re-added to the workflow, open the workflow Xaml (right-click the workflow in Solution Explorer and choose Open With, XML (Text) Editor, click OK, and verify that the following line is present.

xmlns:p1="wf://workflow.windows.net/$Current/$Activities"  

Activity could not be loaded because of errors in the XAML.

If this error occurs when opening the workflow in the workflow designer, press Ctrl+Shift+B to build the solution. This builds the custom activity which is required in order for it to be displayed in the workflow designer.

Could not find type 'DynamicValue' in namespace 'https://schemas.microsoft.com/workflow/2012/xaml/activities'.

Errors such as this can occur because of a mismatch between the samples and the latest version of Workflow Manager Tools 1.0 for Visual Studio 2012. To resolve, first ensure that you have the latest version of Workflow Manager Tools installed from Workflow Manager Tools 1.0 for Visual Studio 2012 installation, and replace all instances of the following line in your XAML files with the subsequent line.

Replace:

xmlns:p="https://schemas.microsoft.com/workflow/2012/xaml/activities"  

With:

xmlns:p="https://schemas.microsoft.com/workflow/2012/07/xaml/activities"  

See Also

Getting Started Tutorial