3 应用程序中嵌入相应流程控制处理
流程模板设计好以后,我们需要开发对应每个Task的执行功能,也就是相关的应用程序,Teamplate的Task可以是Windows Form,也可以是Web Form以及InfoPath表单或者其它的方式。因为精量项目是采用的BS构架的系统,所以本文主要就Web Form的方式做一些总结,设置Task的执行界面是在Task的DefaultForm中设置的,另外还需要设置流程模板的IIS Server以及IIS的物理路径,这两个参数是通过IISServerName属性和IISDirector以属性来设置的,下面的说明中我们主要就用户认证,怎样发起一个新的流程,怎样进行工作流的流转这几个问题来做一个说明。
3.1 用户认证
Teamplate跟AD的集成认证:Teamplate中导入AD用户后可以通过AD做集成认证,具体的方式为通过Teamplate.BLL提供的BSession对象来进行认证,采用BSession.Connect(“”, “”)方法来做用户登录,登录成功后可以获得用户Token,下面是一段用户登录的代码片断:
Teamplate.BLL.BSession bSess = new Teamplate.BLL.BSession();
bSess.Connect("","") ;
string token = bSess.GetToken() ;
bSess.Dispose();
Token是加过密的一个用于用户认证的字符串,在下文中我们可以看到怎样来使用这个Token。
3.2 新建一个流程
对于一个已经创建好的Teamplate流程模板(Model),现在我们来使用它,首先我们要新建一个流程(Process),创建一个新的工作工作流程是使用Teamplate.BLL提供的BProcess对象的Add()方法来实现的,Add方法参数说明请参考Teamplate的帮助文档中的Workflow API Guide,下面是一段创建一个新流程的代码片断:
int FolderId = TeamplateLib.GetFolderId("Processes");
int ModelId = TeamplateLib.GetModelId("Purchase Order");
int ModelOwner = TeamplateLib.GetModelOwner(ModelId);
int UserId = TeamplateLib.GetUserId(username);
BProcess process = new BProcess();
process.SetSessionToken(token);
int ProcessId = process.Add(this.PONo, FolderId, ModelOwner, ModelId);
process.Load(ProcessId);
int TaskID = process.GetNextTaskID(ModelOwner,BProcess.TaskStatus.Ready);
process.UpdateTask(ProcessId,TaskID,DateTime.Today.AddDays(7),UserId,"Normal");
下面对代码做一些说明:
前面四行代码先不看,第5和第6行代码,先声明一个BProcess对象,然后对它进行SetSessionToken,而这个Token就是前面我们登录时获取的那个用户认证字符串!只有对BProcess对象设置了这个Token值后你才有权限使用Add方法新建一个流程,现在应该对Token这个对象有更深的认识了吧。
关注一下Add方法所使用的几个参数,请再看第7行代码,
第一个参数是ProcessName,我们这里用业务表单的流水号来修改它,它可以是空字符串,空字符串时产生的流程名称是在设计Model时输入的DefaultProcessName值后面加上流程的ID号。在这里需要补充说明的一点是ProcessName是不能有重复值的,包括不跟FolderName、ModelName重名,原因是Teamplate在保存这些对象的Files表中Name字段有一个UNIQUE 约束来强制名称的唯一性。
第二个参数是指定放置这个Process的文件夹ID,这个文件夹不是指的物理磁盘的中的文件夹,而是Teamplate系统虚拟的文件夹,具有唯一的ID。
第三个参数指定流程的所有者,微软的网站上介绍Teamplate的文档中是这样描述的:
Teamplate for .NET 也将增强其基于角色(role-based)的安全模型,以充分利用基于人员的工作流服务的不同用户的限制条件。这将保证在一个特定的工作流中,只有创造工作流任务的用户有权委派或分配任务给其他的用户。
很不幸,受微软所吹捧的这一功能在我们的客户面前碰了一个大钉子,客户的需求是:微软文中的创造工作流的用户只能做为一个流程的发起人,而委派或分派任务的权限要交由这个流程模板的管理人员来执行。为了解决这个问题所以有了上面的代码,我们在部署项目时把Model的所有权赋给这个Model的管理人员后,在新建流程之前先获取这个Model的所有人,然后在创建新流程时将流程的所有权限赋给这个Model的所有人(这个值不设置时,默认为就是流程的发起人),从而使Model的所有人获得了Process所有人的权限,问题得到解决。
第四个参数很好理解,就是你要新建Process的Model对应的ID值。
现在可能已经有人对下面的三行代码提出疑义来了,为什么还需要这么一段代码呢?其实很简单,Add一个Process时,默认的第一个Task的执行人就是Add参数中的所有人,那么现在执行权限都给管理拿过去了,也就试所有的流程都交给管理员去做了,我们就不用做事了,^_^!当然是不可以的,要把执行的权限拿回来,所以就有了后面的三行代码,先LoadProcess,获取TaskID,再Update Task的ResponseID(前面有讲过,Task的责任人)。
对最前面的4行代码的解释:代码的功能应该是一目了然,目的是获取后面几个方法所需要的参数。这里唯一需要说明的是TeamplateLib对象不是Teamplate提供的,是我们对Teamplate不直接提供的方法做的一些补充,具体实现是直接在Teamplate数据库中查寻得出的。
3.3 工作流的流转
在Task对应应用程序执行程序时,当业务数据提交时,我们需要将流程往后流转,先看代码:
process = new BProcess();
process.SetSessionToken(token);
process.Load(processId);
this.SaveBindingData(process);
process.WorkflowAdvance(taskId, null);
代码说明:
前面3行代码通过前面的两个例子应该都有所了解,现在来看这个Sample的最关键的一句代码也就是最后一行代码,这一句调用Process的WorkflowAdvance方法来进行流程的流转,详细的说明可以参考Teamplate的帮助文档,这里需要说明的一点是它的第一个参数TaskID,TaskID必须是当前Process的处于Ready状态的Task的ID。
另一个比较重要的说明,代码的第四行用了一个SaveBindingData方法,在这个方法的主要功能是业务数据的保存和保存Process的XML数据。前面在讲设计Model的时候,提到过定义XML数据用于流程流转的控制,在流程流转前,我们就需要根据实际的业务数据将数据保存到之前定义好的XML,然后在WorkflowAdvance方法执行时,就会根据保存的XML数据做为条件根据定义好的业务规则进行控制流转。
浙公网安备 33010602011771号