jBPM建模语言jpdl分析

 

1             swimlane

具有流程角色的意思。一种多个任务由同一个actor执行的机制。swimlane中的第一个任务实例创建后分派时,会为该swimlane记住actor,后续的任务分派时将使用该actorswimlane中的任务不能指定assignmentswimlane中的任务实例分派时,将由swimlane指定的assignment进行分派。swimlane中的第一个任务实例创建时,调用AssignmentHandler,此时传给AssignmentHandlerAssignable是一个SwimlaneInstance

public interface AssignmentHandler extends Serializable {

  void assign( Assignable assignable, ExecutionContext executionContext );

}

public interface Assignable {

  public void setActorId(String actorId);

  public void setPooledActors(String[] pooledActors);

}

TaskInstanceSwimlaneInstance都实现了Assignable

 

 

2             assignment

用于任务分派的元素。

actor-id:执行该任务的actor

pooled-actors:可以执行该任务的actors

两种分派模型:pushpull

push:流程执行分派,调用Assignable.setActorId决定将该任务push到哪个user的任务列表。任务列表的获取:TaskMgmtSession.findTaskInstances(String actorId).

pull:该任务具有多个候选actor。由pool中的actor将任务pull进自己的任务列表。在pull之前任务对pool中的所有actor可见,pull后,actor-id变为pullactor,并在pool中不可见。将actor-id置为null可以将该任务实例重新放回poll。调用Assignable.setPooledActors分派给pooledActors

 

 

3             expression

分派表达式。

identity comoponent:用户、组和许可权的管理,包括组织模型信息。

 

分派表达式示例:

<process-definition>

  ...

  <task-node name='a'>

    <task name='laundry'>

      <assignment expression='previous --> group(hierarchy) --> member(boss)' />

    </task>

    <transition to='b' />

  </task-node>

  ...

 

分派表达式语法:

first-term --> next-term --> next-term --> ... --> next-term

 

其中:

 

first-term ::= previous |

               swimlane(swimlane-name) |

               variable(variable-name) |

               user(user-name) |

               group(group-name)

 

next-term ::= group(group-type) |

              member(role-name)

 

还可在actiondelegationdecision condition中使用类似于JSP/JSF EL的表达式语言,如expression="#{myVar.handler[assignments].assign}"

 

 

4             delegation

用来在流程执行过程中运行用户自定义代码的机制。可用于任务代理。

class(必需):完整类名。

config-type(可选):指定如何实例化和配置delegation对象。若没有则用默认constructor,并忽略配置信息。

fieldconfiguration中的elementnames对应delegation中的域名;

示例:

public class MyAction implements ActionHandler {

  // access specifiers can be private, default, protected or public

  private String city;

  Integer rounds;

  ...

}

对应的配置文件:

...

<action class="org.test.MyAction">

  <city> Atlanta </city>

  <rounds>5</rounds>

</action>

...

 

beanconstructorconfiguration-property

configuration(可选):xml文件,delegation配置信息。

 

 

5             start-state

特殊node:启动节点。可以包含tasktransitioneventexception-handler

 

 

6             transition

源节点是包含该transition的节点,目标节点由to指出。transition的名字是可选的。jBPM的路由功能依赖于transition名字的唯一性。但如果多个transition有相同的名字,将选择第一个。节点transition list中的第一个是其default transition

 

 

7             task

任务定义,指出如何创建和分派任务实例。可以在task-node,也可以在process-definition中定义。process-definition范围内task name必须唯一。

任务可以指定优先级。任务实例可以修改此优先级。

该任务可以属于一个swimlane,此时它的分派由对应的swimlane执行。

duedate指出任务的超时日期。

tasksignalling属性指出当该任务实例完成时,可以发送一个signal给其token来继续流程的执行。taskblocking属性指出当该任务实例没完成之前,与之相关的token不能离开该task-node。默认设置是signallingnon-blocking

 

 

8             task-controller

可选。

任务创建时,可以用controller来移植任务实例变量;任务实例完成时,可以通过controller来向流程实例变量提交任务实例变量。

并不强迫一定要使用controller,仅当有下列需求时使用controller

1)              创建流程实例变量在任务实例中的副本,使得对任务实例变量的改变不会影响流程实例变量。直到流程完成再将任务实例变量提交。

2)              流程实例变量与任务实例变量不是一一对应关系。例如三个流程变量“sales in january”、“sales in februry”和“sales in march”,在任务中可能需要用到的是这三个变量的平均值。

controller在流程变量(process context)和用户接口应用程序之间起一个桥的作用(如下图所示)。当创建任务实例时,controller负责从流程变量中摘录信息来创建任务变量。这些变量作为用户输入提供给用户接口应用。外部输入也存储在任务变量中。当任务结束时,controller负责用任务实例数据更新流程变量。

简单的一对一映射的例子如下:

<task name="clean ceiling">

  <controller>

    <variable name="a" access="read" mapped-name="x" />

    <variable name="b" access="read,write,required" mapped-name="y" />

    <variable name="c" access="read,write" />

  </controller>

</task>

name属性指流程变量名,mapped-name指任务中的变量名。access属性指出是否在任务创建时复制变量,或是否在任务结束后写回流程,或是否是必须的。access是可选的,默认值是"read,write"

如果简单的一一映射不能满足需要,可以自定义TaskControllerHandler接口的实现:

public interface TaskControllerHandler extends Serializable {

void initializeTaskVariables(TaskInstance taskInstance, ContextInstance contextInstance, Token token);

void submitTaskVariables(TaskInstance taskInstance, ContextInstance contextInstance, Token token);

}

并用如下方法定制自己的TaskControllerHandler实现:

<task name="clean ceiling">

  <controller class="com.yourcom.CleanCeilingTaskControllerHandler">

    -- here goes your task controller handler configuration --

  </controller>

</task>

 

 

9             timer

定时器。属性包括timer名、duedaterepeattransitiontransition指出定时器到时间时要执行该transition

向节点加入timer最简单的方法是在节点定义中加入timer元素:

<state name='catch crooks'>

  <timer name='reminder'

         duedate='3 business hours'

         repeat='10 business minutes'

         transition='time-out-transition' >

    <action class='the-remainder-action-class-name' />

  </timer>

</state>

节点中指定的timer在离开该节点后不会执行。transitionaction都是可选的。当执行一个timer会顺序发生如下事件:

1)  发送timer类型事件;

2)  如果指定了action,则执行该action

3)  如果指定了transition,则通过该transition发送signal来恢复流程执行。

timer必须有唯一的名字,若没有指定timer名,将使用node名作为其名字。

timeraction创建和取消,分别是create-timercancel-timer

 

 

10       action

action可以放在event中,也可以放在node中。每个event都有一个action list,当发送一个event时,执行该eventaction list中的所有actionevent中的action执行不会影响流程执行控制流。node中的action则要负责流程执行的传递。

class指出action处理类,实现了ActionHandlerconfig-type指出如何配置该actionhandler类。如下示例:

public class RemoveEmployeeUpdate implements ActionHandler {

  public void execute(ExecutionContext ctx) throws Exception {

    String firedEmployee = (String) ctx.getContextInstance().

getVariable("fired employee");

    Connection connection = ctx.getProcessInstance().

getJbpmSession().getSession().getConnection();

    Statement statement = connection.createStatement();

    statement.execute("DELETE FROM EMPLOYEE WHERE ...");

    statement.execute();

    statement.close();

  }

}

对应流程定义:

<process-definition name="yearly evaluation">

 

  ...

  <state name="fire employee">

    <transition to="collect badge">

      <action class="com.nomercy.hr.RemoveEmployeeUpdate" />

    </transition>

  </state>

 

  <state name="collect badge">

  ...

 

</process-definition>

actionnameref-nameref-name可以放在任何能指定action的地方。ref-name的使用用来限制复杂action configuration的副本。或用于运行时action的执行的调度。

accept-propagated-events:是否允许事件沿着node—superstate—processdefinition进行传递。

 

 

11       event:

可以出现在process-definitionnodetransition中。

属性由事件类型指出。有4task-event类型:task-createtask-assigntask-starttask-end。一个事件对应有一个action list,当该事件发生时,执行list中的所有action

可以定制自己的事件类型,通过GraphElement.fireEvent(String eventType, ExecutionContext executionContext)来发送事件。

 

 

12       script

也是一种action,它用来执行beanshell script。默认情况下,script可以使用processtasktokennodeexecuteContexttaskInstance的所有variable作为自己的script variable,但script variable不能写回到process variable

如下示例:

 

<process-definition>

  <event type="node-enter">

    <script>

      System.out.println("this script is entering node "+node);

    </script>

  </event>

  ...

</process-definition>

可以在script中包含expressionvariable子元素。variable元素的使用用来定制载入和存储变量的默认行为。如下示例:

<process-definition>

  <event type="process-end">

    <script>

      <expression>

        a = b + c;

      </expression>

      <variable name='XXX' access='write' mapped-name='a' />

      <variable name='YYY' access='read' mapped-name='b' />

      <variable name='ZZZ' access='read' mapped-name='c' />

    </script>

  </event>

  ...

</process-definition>

 

create-timercancel-timer是创建和取消定时器的action

 

 

13       exception handler

 

process-definitionnodetransition中可以指定一个exception handler list。每个exception handler都有一个action list。都发生exception时,在产生exceptiondelegation类所属层次结构中查找对应的exception-handler,找到则执行handler中的所有action

java异常处理机制不同,不能改变控制流。exception可以是caught,也可以是uncaughtexception可以由exception-handler caughtuncaught exception被抛给client。对于caught exception,图的执行会和没抛出exception一样继续执行。

在处理exceptionaction中,通过调用Token.setNode(Node node)可以将token放在图中的任意node

 

 

14       node element

                                  node

node类型的节点用于需要在node中执行用户自定义的代码。node类型节点有一个action,当执行到该节点时,执行actionactionhandler中的代码可以做任何你想做的事情,但要负责流程执行的继续。

所有节点类型都有name属性,async="true"时,表示流程可以异步执行。

 

                                  state

 

state本质上是一个wait state。它与task-node不同的地方是它不会创建任务实例。它可以用于与外部系统的交互。当进入该节点,向外部系统发送消息,然后等待,直到外部系统将响应消息发回该节点,导致调用token.signal(),从而触发流程的继续执行。

 

 

                                  task-node

 

任务分派节点。

task-nodesignal属性值:

last

last-wait

first

first-wait

unsynchronized

never

create-tasksbooleandefault="true",该节点执行时是否创建任务实例。

end-tasksbooleandefault="false",该节点执行完后,若其中的任务实例没有end,是否将其end

 

 

                                  super-state

一组节点的集合,可以嵌套,这给流程定义带来层次性结构。jBMP中可以将任意的节点组合成super-state。这些super-state通常代表应用的某个阶段。

superstate transition:所有离开该super-statetransition都可以由内部节点的token执行。transition可以到达superstate,此时token将被重定向到superstate的第一个节点。superstate外部的节点可以transition到内部节点,内部节点可以transition到外部节点,也可以到superstate自身。

superstate eventsuperstate专有的两个eventsuperstate-entersuperstate-leave。只要进入superstate就发送superstate-enter事件,只要离开superstate范围(不管是内部哪个node,只要是transition到外部node),就发送superstat-leave事件。

层次结构名:节点在节点集范围(流程或superstate)内,名字要唯一。可以通过层次名来引用。

<process-definition>

  ...

  <super-state name="phase one">

    <state name="preparation">

      <transition to="../phase two/invite murphy"/>

    </state>

  </super-state>

  <super-state name="phase two">

    <state name="invite murphy"/>

  </super-state>

  ...

</process-definition>

 

 

                                  process-state

用来执行子流程的节点。当进入该process-state,创建sub-process实例并执行,直到(default async="false"sub-process结束,才继续super process的执行。

一个process-state的例子:

<process-definition name="hire">

  <start-state>

    <transition to="initial interview" />

  </start-state>

  <process-state name="initial interview">

    <sub-process name="interview" />

    <variable name="a" access="read,write" mapped-name="aa" />

    <variable name="b" access="read" mapped-name="bb" />

    <transition to="..." />

  </process-state>

  ...

</process-definition>

 

 

                                  fork

分支节点,将执行路径分解为多个并发执行路径,默认情况下,为每个离开该forktransition创建一个子token,与到达该forktoken构成父子关系。

 

                                  join

默认情况下,到达join节点的token都必须有相同的父token,也就是这些token由同一个fork split出来。join负责end到达该节点的子token。当所有子token到达join,才继续父token的执行。joinleaving transition是唯一的。

 

                                  decision

判断节点。有两种判断模型,一种由process进行判断(在process-definition内),一种由外部实体(即不是process-definition的一部分)决定判断结果。

如果是流程决定判断,一种简单的办法是在transition中加入conditionconditionbeanshell expression,它返回boolean值。运行时,decision节点在其leave transition中按它们定义顺序循环,直到找到第一个condition计算结果为truetaketransition。另一种办法是指定DecisionHandler,由该handler计算要taketransition返回给decision

当由外部实体决定判断结果时,需要执行多次转换。即在decision前的wait state与外部实体交互,获取的结果进入decision进行判断。

 

                                  end-state

流程结束节点。

 

 

◎╭╮◎  ╰╯╰╯  ﹌﹏﹌

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值