Activiti7
简述:
Activiti是一款工作流引擎,是业务流程管理(BPM)框架,最常用的是用在各种审批工作中,比如请假审批,采购审批
引进背景:
我们引入工作流是为了灵活多变的实行客户在提交订单时,获得上级认证通过的流程方式,采用流程图可以在不修改代码,不发布的前提下,满足客户的需求,
在上线初, 存在业务场景为“三不固定”审批:
节点不定:客户上级审批存在多个节点审批,一级复一级,节点不定
人员不定:一个节点审批存在多个人审批的情况,可一可众,人员不定
路线不定:同一个人下单,存在依据下单条件多种,多条分支,不同审批人的情况,路线不定
在这种复杂的业务场景和业务需求下,传统的开发审批功能模块是无法满足的,故而引入了Activiti工作流,与之相比的还有Flowable 引擎,这两个都是比较热门的同种引擎,但是在接口文档完整性,版本稳定性,开源特性等多个方面考虑,最终选择了Activiti,需要注意的是,我们采用的act版本是7.0.0版本,这个版本强耦合了Security安全框架,我们项目采用的是轻量级框架Shiro,故而我们使用了UserDetailsServiceImpl类实现了Security中的UserDetailsService类,
伪装登录到了Security中,
/**
* activiti7强绑定了security中的角色,shiro在此伪装登录一次
* @param username
* @return
* @throws UsernameNotFoundException
*/
@Override
public UserDetails loadUserByUsername(String username) throws UsernameNotFoundException{
String userPasswordDb = new BCryptPasswordEncoder().encode("password");
String permissions = "ROLE_ACTIVITI_USER,GROUP_activitiTeam";
UserDetails userDetails =
new User(username, userPasswordDb,
AuthorityUtils.commaSeparatedStringToAuthorityList(permissions));
return userDetails;
}
与之相关的还有LoginToSecurityApplicationConfiguration中的方法,以及SecurityUtil#logInAs 有兴趣的可以看看:
@Autowired
private UserDetailsServiceImpl userDetailsService;
public void logInAs(String username) {
//======================= start ====================================
UserDetails user = userDetailsService.loadUserByUsername(username);
if (user == null) {
throw new IllegalStateException("User " + username + " doesn't exist, please provide a valid user");
}
SecurityContextHolder.setContext(new SecurityContextImpl(new Authentication() {
@Override
public Collection<? extends GrantedAuthority> getAuthorities() {
return user.getAuthorities();
}
@Override
public Object getCredentials() {
return user.getPassword();
}
@Override
public Object getDetails() {
return user;
}
@Override
public Object getPrincipal() {
return user;
}
@Override
public boolean isAuthenticated() {
return true;
}
@Override
public void setAuthenticated(boolean isAuthenticated) throws IllegalArgumentException {
}
@Override
public String getName() {
return user.getUsername();
}
}));
//======================= end ====================================
org.activiti.engine.impl.identity.Authentication.setAuthenticatedUserId(username);
}
正文:
工作流的核心是 ProcessEngine 接口,ProcessEngine接口定义了获取各种服务类实例对象的方法,我们主要用到的是这四个RepositoryService,RuntimeService,TaskService,HistoryService,具体用法在Activiti中都有阐述,
工作流作为一个工作引擎,有他自己的专属25张表,
Activiti使用到的表都是ACT_开头的。
ACT_RE_:流程定义存储。
ACT_RU_:流程执行记录,记录流程启动到结束的所有动作,流程结束后会清除相关记录。
ACT_ID_:用户记录,流程中使用到的用户和组。
ACT_HI_:流程执行的历史记录。
ACT_GE_*:通用数据及设置。
表说明如下
act_evt_log --流程定义,详细信息
act_ge_property --属性数据表。存储这个流程引擎级别的数据。
act_procdef_info
act_re_model
–流程部署相关的三张表
act_re_procdef --业务流程定义数据表
act_re_deployment --用来存储部署时需要持久化保存下来的信息
act_ge_bytearray --用来保存部署文件的大文本数据
–流程历史数据,以hi标识,记录流程运行所有信息
act_hi_actinst --流程实例
act_hi_attachment
act_hi_comment --提交审核意见表
act_hi_detail --启动流程或者在任务complete之后,记录历史流程变量
act_hi_identitylink --任务参与者数据表。主要存储历史参与者的信息。
act_hi_procinst --流程实例
act_hi_taskinst --任务实例
act_hi_varinst --历史流程变量数据表
–流程运行时临时数据,以ru标识,流程运行完毕,对应数据消失,表说明参考历史信息
act_ru_deadletter_job
act_ru_event_subscr
act_ru_execution
act_ru_identitylink
act_ru_integration
act_ru_job
act_ru_suspended_job
act_ru_task
act_ru_timer_job
act_ru_variable
–系统业务表
shop_act_info --自定义流程业务表,流程业务和订单业务绑定表
shop_process_model --自定义流程模板表,流程模板表,记录系统新建了哪些流程图
包括部署流程、启动流程、扭转流程、完成流程、驳回流程、填写审批原因、查询流程列表、查询流程流水、反射获取节点上配置的参数等。如没有所需的方法可以从网上获取。
前端引入了Bpmn画图工具,能够绘制流程图,页面如下:
排他网关配置如下:
配置完成后,需要部署流程图,部署流程图之后,流程方才生效,流程图有版本之分,业务单据所绑定的历史流程不会更改,还会依照历史版本的流程图运行