<!----><!----> <!---->
2. 流程同步服务
流程同步服务是引擎自定义的一个对流程实例和流程定义的锁的定义,譬如在做指定下一个环节的参与人 (WFAppointParticipantManager 中的appointNextActParticipant 方法)时先把当前的流程实例给琐住 (ServiceFactory.getLockService().lockProcInstance )。然后在方法结束后再把流程实例的锁给释放 (ServiceFactory.getLockService().releaseProcInstance )。在同步服务中定义了两种类型的锁,一种 是流程定义锁,一种是流程实例琐(两个list ),在加琐时检查改ID (流程实例ID 或流程定义ID )是否已经在琐列表中,如果在则加琐。在加琐与解锁之 间是通过一个线程来操作锁列表(waitingList )实现的。其实现方法大概是在加锁的时候向waitingList 添加一个锁对象,然后把线程 wait(); 在解锁的时候向waitingList 减去一个锁对象,并把线程notify() 。流程同步服务的实现方式还是比较复杂的。尽管只用了七八 个类。
3. 组织机构管理
EOS 提供了一套自己的组织机构模型,我们在安徽服务保障三期中引用了该模型。该组织机构模型的服务会话面的实现是在配置文件中配置的,然后引 擎采用java 的反射机制加载配置类(在引擎中有个叫做“ 服务定位器” 来实现,该服务定位器和我们平时用的一样,只是它是从文件中读取服务定义,隐藏了具 体寻址细节)。如果不用EOS 提供的组织机构模型可以实现WFOMService 接口,并实现里面的方法。估计EOS 的原意是提供组织机构模型和引擎服务 的松偶合,但在其引擎的实现上好象并没有做到。
OMServiceImpl 类是引擎默认加载的组织机构模型会话面类。该类定义了人员,角色,机构等等,OMServiceImpl2 类包含岗 位的组织机构模型(目前的引擎的还不支持,没有搞清楚EOS 没有把岗位纳入组织机构模型中),但EOS 提供的开源的组织机构模型中并不支持。
4. 审计服务
该服务记载了所有流程模板的变更和对流程实例的操作历史。引擎共定义了39 种审计类型,包括模板变更,启动流程,完成工作项等等。由于审计的类 型代码和引擎的事件代码,所以引擎在中间做了一层映射,把事件代码和审计代码一一对应(审计代码多于事件代码)。在审计过程中其实是往审计表中加一条历史 记录。
5. 日志服务
引擎的LOG 服务很简单,和我们平时用的LOG 差不多。在打日志的时候传入JVM 唯一实例的日志上下文WFLogContext ,在该类中定义 了一条日志所需要的日志头,比如等级(@level ),操作员(@operator ),sql (@sql ),时间戳(@timestamp )等等。然后在 具体打某一条日志的时候把日志头和日志内容拼装起来形成一条日志。
引擎的日志实现了日志的读写,引用了log4j 的RollingFileAppender 和PatternLayout 。并提供了类似AOP 的方法前后拦 截打日志的服务(不知道方法前后的拦截日志是在代码中人工加上的还是由AOP 代理自动加载的,因为采用了AOP 时在编译的时候就把代码插入到要拦截的切入 点中去)。
6. 持久层服务
引擎的持久层和studio 里的持久层是采用一样的设计。大概是把数据库的字段和持久层的XML 定义一一对应,没有采用像hibernate 或 者EJB 的CMP 或者BMP 那样很复杂的OR_mapping 。由JDBC 驱动持久层在系统中显的很高效,但采用数据库和持久层的XML 描述文件一一对应 所以没有把关系数据的对象化做的很别致。(没有深入的看过代码,可能我理解的不对)。
7. 引擎的缓存
工作流引擎的缓存是通过一个HashMap 来维护的。用有以下几类缓存:流程实例的缓存;活动实例的缓存;工作项的缓存;相关数据的缓存;相关 数据Dom 的缓存;流程属性数据的缓存,以上几类的实例缓存个数是通过在配置文件中配置的,还有一类流程模板的缓存是在引擎启动的时候就解析流程模板的 XML 文的定义(因为流程定义是通过XML 文来存储在数据库中),解析成流程定义对象并加载到内存中。
7.1. 缓存的配置
工作流缓存的配置是在wfconfig.xml 文件中配置的。共有以下几种配置:
7.2. 缓存的实现
在引擎启动的时候取得工作流配置信息,如果允许使用缓存则初始化上面所述的六类缓存。在初始化的时候引擎默认缓存的存活时间为 0x1499700L 。缓存的大小为配置文件所配。这样则生成在JVM 里的六个Cache 类的实例。每个Cache 都有一个HashMap 的属性,这里面 存储了要缓存的对象。在CacheFactory 类中又有一个HashMap 对象属性,这个对象存储的是Cache 对象的集合。就是上面所述的六个 Cache 类实例的集合。普元的开发人员把该对象起名为Caches 。那么在取某个活动实例时就先中缓存中读取,如果找到则直接返回,如果没有则从数据库 中加载。
引擎的缓存并不是直接把从数据库中取得的对象put 到map 中,而是做了一层优化,把从数据库中找到的对象封装成CacheObject 对象, 该对象有个链表(LinkedList )的属性对象。该对象有前驱和后继节点,其节点就是我们要put 的对象。其具体的优化策略和大多数缓存一样,采用最 近最多访问策略,共有两个列表维护,一个是最近访问对象位于首位,一个是最多访问对象位于首位。