详解WF 4.0中如何实现子流程

开发 后端
本文将为大家介绍WF 4.0中,如何在主流程中启用一些子流程,并通过简单实例来详细介绍实现过程。

在WF 4.0中,存在不同种类的流程。本文将介绍的子流程如何在主流程中实现的原理,希望对大家有所帮助。

工作流服务中,经常会在主流程启用一些子流程。我在审批流程中经常会使用bookmark来暂停流程,这篇文章,将结合bookmark来实现主流程启动子流程。

使用以前的一篇WF4.0自定义持久化中的自定义的持久化。不过数据表中加入了一个字段parentid,用于标识父流程:

代码

下面用一个流程实例为例说明主流程是如何启用子流程,子流程又是如何返回主流程的,主流程如下:

主流程

***个节点“***站审核”和第三个节点“第二站审核”都是BookMark书签,附BookMark的代码如下:

代码

public sealed class Read<TResult> : NativeActivity<TResult>  
    {  
        public Read()  
            : base()  
        {  
        }  
 
        public string BookmarkName { getset; }  
 
        // Define an activity input argument of type string  
        public InArgument<string> Text { getset; }  
// Must return true for a NativeActivity that creates a bookmark  
        protected override bool CanInduceIdle  
        {  
            get { return true; }  
        }  
 
        protected override void Execute(NativeActivityContext context)  
        {  
context.CreateBookmark(this.BookmarkName, new BookmarkCallback(this.Continue));  
        }  
 void Continue(NativeActivityContext context, Bookmark bookmark, object obj)  
        {  
            this.Result.Set(context, (TResult)obj);  
        } 
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 25.

第二个节点“启用子流程”,它是一个自定义的节点,代码如下:

代码

public sealed class CallChild : Activity  
   {  
 
       public string FlowName { getset; }  
 
       public CallChild()  
       {  
  base.Implementation = new Func<Activity>(CreateBody);  
       }  
 
       public Activity CreateBody()  
       {  
 
           return new Sequence  
           {  
               DisplayName = "子流程",  
               Activities =  
                   {     
                       new ChildCodeActivity  
                       {  
                           FlowName=this.FlowName        
                       }  
                       ,  
                       new Read<string>  
                       {  
                           BookmarkName="CallChild",  
                          
                       }                   
                   }       };        }    } 
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.
  • 20.
  • 21.
  • 22.
  • 23.
  • 24.
  • 25.
  • 26.
  • 27.
  • 28.
  • 29.

注意上面的ChildCodeActivity类,实际上是在ChildCodeActivity中启动子流程的,ChildCodeActivity后面是一个书签,用于暂停主流程。当子流程完成后,在子流程中恢复这个书签,子流程结束,主流程继续往下跑。这个活动中有一个FlowName属性,用于表示是启用哪个子流程。ChildCodeActivity代码如下:

代码

sealed class ChildCodeActivity : CodeActivity  
    {  
// Define an activity input argument of type string  
        public string FlowName { getset; }  
// If your activity returns a value, derive from CodeActivity<TResult>  
// and return the value from the Execute method.  
        protected override void Execute(CodeActivityContext context)  
        {  
            Guid ChildGuid;  
            ChildGuid = WorkFlowRun.CreateAndRun(FlowName);  
InstancesTable obj = InstancesTableBiz.GetInstancesTable(ChildGuid);
//取得子流程的id  
            obj.parentid = context.WorkflowInstanceId;  
            InstancesTableBiz.UpdateInstancesTable(obj);//跟新父流程id  
        }  
    } 
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.

WorkFlowRun.CreateAndRun(FlowName)根据FlowName启动相应的子流程,并得到实例的Guid。并将子流程的parentid修改改成主流程的guid。

子流程的示例如下:

子流程的示例

#T#

子流程的***个节点“子流程***站审核”和第二个节点“子流程第二站审核”也都是BookMark书签。

***一个节点是“结束”。这个节点也至关重要,因为我是使用这个节点,从子流程中返回到主流程的。因此,每个子流程都会有End节点,它的代码如下:

代码

public sealed class End : CodeActivity  
  {  
      // Define an activity input argument of type string  
      public InArgument<string> Text { getset; }  
 
 // 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 text = context.GetValue(this.Text);  
          Guid id = context.WorkflowInstanceId;  
          InstancesTable Obj = InstancesTableBiz.GetInstancesTable(id);  
          if (Guid.Empty != Obj.parentid)//如果是子流程,返回父流程  
          {  
  WorkFlowRun.Submit(Obj.parentid, "ParentProcess""returnMain");  
          }  
      }  
  } 
  • 1.
  • 2.
  • 3.
  • 4.
  • 5.
  • 6.
  • 7.
  • 8.
  • 9.
  • 10.
  • 11.
  • 12.
  • 13.
  • 14.
  • 15.
  • 16.
  • 17.
  • 18.
  • 19.

这是我思考出的在WF4.0中一个启用子流程的方案,如果你有什么更好的方案和建议,请给我留言,谢谢。

原文标题:WF4.0中实现子流程

链接:http://www.cnblogs.com/zhuqil/archive/2010/01/31/SubProcessDemo.html

责任编辑:彭凡 来源: 博客园
相关推荐

2010-01-14 14:12:14

Visual Stud

2009-07-16 10:41:40

WF 4.0 beta

2010-01-14 09:35:10

WF4.0

2009-06-15 10:20:47

WF 4.0 Beta跟踪机制

2009-10-28 09:23:27

WF4.0 Beta2

2009-06-17 10:51:58

WF4.0规则引擎

2009-06-22 09:36:06

WF 4.0 beta跟踪配置

2009-10-22 08:54:56

WF4 Beta 2

2009-12-04 09:14:05

.NET 4.0

2009-10-20 15:03:29

ExpandoObje

2009-03-23 10:54:12

.NET契约式编程编程思想

2023-11-29 15:53:45

2010-01-05 09:26:13

.NET 4.0

2009-05-20 10:26:09

Visual StudWF微软

2009-07-24 10:00:38

.NET 4.0内存映

2009-09-27 10:03:53

Silverlight

2023-10-04 09:44:56

Btrfs子卷

2011-08-29 14:59:26

QtEvent事件

2009-06-03 14:50:17

C# 4.0泛型协变性

2009-12-31 16:56:40

Silverlight
点赞
收藏

51CTO技术栈公众号