Introduction
The intercommunication between a Workflow and the Host application is not a trivial thing to implement because the host and the workflow run in different threads. Microsoft has developed a communication structure that simplifies the problem. It creates a special methodology and class to handle the communication.
In this series of articles, I try to show the different possibilities to implement the communication, from the simplest case to the more complex. I am not planning to be exhaustive, but I will try to give a general panoramic view in order to give you a good idea about the thematic.
WorkFlow和主程序运行在不同的线程,不能直接通信。Microsoft 对此有专门的方法。
Because I don’t like large articles, I have divided this in to the followings parts:
- Part I: Simplest communication case: Communication from Host to Workflow by using parameters.
- Part II: Intercommunications Workflow -> Host through the CallExternalMethod activity.
- Part III: Intercommunications Host -> Workflow through the HandleExternalEvent activity.
- Part IV: Organisation of the communication classes: Communication manager, wca.exe utility, and the Wwca.exe Windows front-end for wca.exe.
- Part V: Intercommunications with a Workflow instance using the Correlation parameter.
Background
In this first article, I will explain with an example a basic form to pass information from the Host to the Workflow.
本篇解释一种简单的方式。
This possibility to pass initialization parameters to the Workflow is very useful in case that we need to pass information only when the Workflow is launched and need not communicate any more.
当workflow启动时需要把初始变量传进来。
Considerer a situation where you want to read a file from the computer and see a determinate number of chars from it.
假设你想从一个文件中读取编号,需要两个变量(文件路径和号码)
We can pass two parameters (the file path and the number of characters to return from the file) and the Workflow will show the information in an internal message box (see Figure 1).
You can see that the barrier between the threads is passed with the Workflow invocation and the message is directly shown in the Workflow thread. We use a console application and a sequential Workflow to explain how to proceed in this situation.
Using the Code
Create a sequential console Workflow project in Visual Studio 2008. This action creates a Program.cs console file and a Workflow1.cs file. You should include a reference to System.Windows.Form in the project References before following these steps.
The steps to pass parameters to the Workflow are relative simple. They are shown here:
- Create two properties to hold the input parameters in Workflow1.cs (code), as show in the following code segment: 创建2个属性保存输入的参数
Collapse Copy Code
public sealed partial class Workflow1: SequentialWorkflowActivity { //Enter the variables that hold the parameters as properties string _filepath = string.Empty; int _quantity = 0; //Variable to hold the result string _result = string.Empty; /// <summary> /// The Property name must be the same as the object in the /// input parameter dictionary /// </summary> public int Quantity { get { return _quantity; } set { _quantity = value; } } /// <summary> /// The Property name must be the same as the object in the /// input parameter dictionary /// </summary> public string FilePath { get { return _filepath; } set { _filepath = value; } }
- Create a
Dictionary
to hold the Workflow input parameters. This action takes place in the Host application. We must create aDictionary
with the following structure: 使用一个Dictionary 保存workflow的输入参数,这个动作在主程序中Collapse Copy CodeDictionary<string, object>
Each object in the dictionary must have the same index name as the property declared at point 1 in the Workflow. In our example, the properties are “
FilePath
” and “Quantity
”. 在dictionary 中的对象必须和workFlow中声明的属性用同样的名字In the example, we have the possibility to enter these parameters as line parameters, but you can get the value of these parameters from anywhere. In the following code, you can see how to prepare the dictionary to fill the Workflow properties from the local variables:
Collapse Copy Code//Create a dictionary to pass parameter to workflow.... Dictionary<string, object> argumentDictionary = new Dictionary<string, object>(); //Pass the first parameter: the file path. You must use the same name //that was defined as variable in the workflow. argumentDictionary.Add("FilePath", _filepath); argumentDictionary.Add("Quantity", _readQuantity);
- Pass the created dictionary to the Workflow.
When the Workflow is created in the Host application, the
CreateWorkflow
function has an overloaded method that gives you the chance to initialize the Workflow with an arbitrary number of parameters. You can see the function in the following code segment: 当workflow在主程序中创建时,CreateWorkFlow这个函数会用给定的参数启动workFlowCollapse Copy CodeWorkflowInstance instance = workflowRuntime.CreateWorkflow( typeof(SimplestWFHostComm.Workflow1), argumentDictionary ); instance.Start();
The Workflow-Runtime instantiates the Workflow and automatically tries to match the values in the dictionary with the declared properties in the Workflow. If they match, the values are transferred to the properties. If you pass a name in the dictionary that does not have a correspondence with a property in the Workflow, or you pass an object with an erroneous type, an exception of type
ArgumentException
is raised.
That is all! To complete the project, see the code in the attachment and incorporate the program logic in your project, or if you want, run the attached code.
I use, by default, a file that is in System32, and I think that all Windows OSs have it. But maybe you don’t have it in your system! Feel free to modify this parameter for a file that you have. Use only a text file as the FilePath
parameter, and if you use a file or path with white space, you must to use quotation marks to surround it.
Resume
The three basic steps to pass initialization parameters from a Host to a Workflow are:
- Create the necessary properties in the Workflow to receive the parameters.
- Create a
Dictionary
instance in the Host application to hold the initialization parameters. - Pass the
Dictionary
as a parameter to the Workflow-RuntimeCreateWorkflow
method.
As you can see, passing initialization parameters from a Host to a Workflow is not very complicated. This relative simple technique is also very useful for many real life situations but not sufficient.
In the example we have considered, we only need to pass information to the Workflow, but what about when the Workflow needs to pass information to the Host application? We will talk about this in the next article.