WF(七)----其他服务

调度程序服务

调度程序服务负责为运行时提供实际执行工作流的线程。工作流的实例只会在一个线程上执行,引擎本身可以同时调度多个线程来执行不同的工作流实例。工作流实例的数目很有可能要比应用程序可用的的线程数目要大。所以,运行时需要使用某种方式为工作流实例安排线程,而具体实现时通过调度程序服务实现的

DefaultWorkflowSchedulerService,实现了运行时的默认行为,它使用.NET线程为执行工作流提供线程。另外还有ManaualWorkflowSchedulerService。他们都继承自WorkflowSchedulerService

 

 

下面为DefaultWorkflowSchedulerService的三个属性:

 

 

注意,MaxSimultaneousWorkflows ,它指定了同时最多可以有多少条线程执行工作流。默认情况下,它被设置成机器上处理器个数的倍数;它可以随意被更改,但是需要注意,调度服务本身需要一个线程,所以将MaxSimultaneousWorkflows 和MaxThreads设为相等会很不好,会照成死锁:因为调度服务可能会得不到线程饥饿。另外默认调度程度服务使用的线程库是系统线程库,所以还会有其他线程会要用到这些线程。所以一般也不推荐使MaxSimultaneousWorkflows的值与最大线程数接近

 

什么情况下,我们会需要ManaualWorkflowSchedulerService?大多数智能客户端应用程序使用默认调度服务。使用Windows Forms和WPF技术的应用程序可能希望在执行工作流的时候用户界面仍然可以响应,所以它需要在线程池中的线程上异步执行工作流。

服务器端应用程序的工作方式就不一样了。服务器端应用程序总是希望使用最少的线程去尽可能多的处理客户端请求。当线程被调度用来执行工作里时,IIS可以用来处理新请求的线程数目自然就少了。

Web应用程序和Web Services的ASP.NET Runtime已经使用线程池中的线程来处理HTTP请求了。异步的工作流执行过程使用默认调度器,这只会为每个请求都捆绑一个附加线程。所以服务器端应用程序通常会使用手工调度器并将处理请求的线程贡献给工作流。解决方法很明显:ASP.NET页面在工作流做了某些工作到达空闲状态或者完成状态前是不能提前完成的,所以,我们直接使用这个线程,这时候你可能希望使用ManaualWorkflowSchedulerService。

典型的使用ManaualWorkflowSchedulerService的代码如下:

WorkflowRuntime runtime1 = new WorkflowRuntime();

ManualWorkflowSchedulerService scheduler= new ManualWorkflowSchedulerService();

runtime1.AddService(scheduler);

//这里也可以使用转载服务创建实例

   WorkflowInstance instance = runtime1.CreateWorkflow(typeof(Workflow1));

   instance.Start();

   scheduler.RunWorkflow(instance.InstanceId);

 

使用手工调度器运行工作流,首先,我们调用工作流实例的Start方法来安排工作流运行。但调用Start方法只是让Runtime做好准备,而不是真正运行工作流。想要执行工作流,我们还得显式调用手工调度服务的RunWorkflow方法并传入工作流实例ID。手工调度服务将使用调用方的线程来同步的执行工作流。这个过程就是宿主贡献线程的过程

更多详细的信息(比如配置文件的方式)可以参考:《WF编程》系列之42 - 承载工作流:调度(Scheduling)服务 

装载服务(WorkflowLoaderService

装载服务负责将输入的XML流转换成可以执行的工作流定义。DefaultLoaderService(默认装载服务)假定输入的XML流石XAML。当调用workflowRuntine.CreateWorkflow()方法传入XmlReader参数时,这个服务就会被触发(将类型作为参数传入时不会)。

创建定制的装载服务,是将流程的现有XML描述映射成工作流定义的一种有效方式。工作流仅仅由一个活动树组成,所以根据XML文件的结构进行解析可以很快的创建这样的活动树并交给运行时执行。

 

队列服务(WorkflowQueuingService

WorkflowQueuingService是一种不可以被重写的运行时服务,它负责管理工作流实例使用的队列。WF利用这些内部队列作为所有工作流和活动之间通信的基础

WF 提供的通信模型是构建于队列系统的基础之上,我们可以使用自定义活动来注册以接收关于队列的消息,而宿主应用程序中的服务则发送关于队列的消息。自定义活动可以使用此模型来处理外部事件,也可以传递异步活动执行的完成。这样,您的活动可以先执行到某一点,然后等待激发因素的到来以便继续执行。下图描述了宿主应用程序中的代码与工作流中的代码(或活动)之间的通信模型。

下图描述了宿主应用程序中的代码与工作流中的代码(或活动)之间的通信模型。

 

下面这张图是WF类库中和队列相关的三个类:

 

想要在自定义活动侦听消息是否到达某个队列,可以参考:坚持学习WF(11):工作流通信与队列 

posted @ 2009-05-15 16:41  碧海山城  阅读(413)  评论(0)    收藏  举报