Skip to content

Commit 06df1b2

Browse files
committed
fix trySubmitFlow bug
1 parent 004a90e commit 06df1b2

File tree

11 files changed

+184
-21
lines changed

11 files changed

+184
-21
lines changed

pom.xml

+1-1
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212

1313
<groupId>com.codingapi.springboot</groupId>
1414
<artifactId>springboot-parent</artifactId>
15-
<version>2.9.8</version>
15+
<version>2.9.9</version>
1616

1717
<url>https://github.com/codingapi/springboot-framewrok</url>
1818
<name>springboot-parent</name>

springboot-starter-data-fast/pom.xml

+1-1
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
<parent>
66
<artifactId>springboot-parent</artifactId>
77
<groupId>com.codingapi.springboot</groupId>
8-
<version>2.9.8</version>
8+
<version>2.9.9</version>
99
</parent>
1010
<modelVersion>4.0.0</modelVersion>
1111

springboot-starter-flow/pom.xml

+1-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
<parent>
77
<artifactId>springboot-parent</artifactId>
88
<groupId>com.codingapi.springboot</groupId>
9-
<version>2.9.8</version>
9+
<version>2.9.9</version>
1010
</parent>
1111

1212
<name>springboot-starter-flow</name>

springboot-starter-flow/src/main/java/com/codingapi/springboot/flow/domain/FlowNode.java

+16-6
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,9 @@
1919
import lombok.Setter;
2020
import org.springframework.util.StringUtils;
2121

22+
import java.util.Comparator;
2223
import java.util.List;
24+
import java.util.stream.Collectors;
2325

2426
/**
2527
* 流程节点
@@ -101,21 +103,30 @@ public class FlowNode {
101103
*/
102104
private List<FlowButton> buttons;
103105

106+
/**
107+
* 按钮顺序
108+
*/
109+
public List<FlowButton> getButtons() {
110+
if (buttons != null) {
111+
return buttons.stream().sorted(Comparator.comparingInt(FlowButton::getOrder)).collect(Collectors.toList());
112+
}
113+
return null;
114+
}
104115

105-
public void verify(){
116+
public void verify() {
106117
if (this.titleGenerator == null) {
107118
throw new IllegalArgumentException("titleGenerator is null");
108119
}
109120
if (this.operatorMatcher == null) {
110121
throw new IllegalArgumentException("operatorMatcher is null");
111122
}
112-
if(timeout<0){
123+
if (timeout < 0) {
113124
throw new IllegalArgumentException("timeout is less than 0");
114125
}
115-
if(!StringUtils.hasLength(id)){
126+
if (!StringUtils.hasLength(id)) {
116127
throw new IllegalArgumentException("id is empty");
117128
}
118-
if(!StringUtils.hasLength(code)){
129+
if (!StringUtils.hasLength(code)) {
119130
throw new IllegalArgumentException("code is empty");
120131
}
121132
}
@@ -206,8 +217,7 @@ public FlowRecord createRecord(long workId,
206217
String title,
207218
IFlowOperator createOperator,
208219
IFlowOperator currentOperator,
209-
BindDataSnapshot snapshot
210-
) {
220+
BindDataSnapshot snapshot) {
211221

212222
// 当前操作者存在委托人时,才需要寻找委托人
213223
IFlowOperator flowOperator = currentOperator;

springboot-starter-flow/src/main/java/com/codingapi/springboot/flow/matcher/OperatorMatcher.java

+11
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,17 @@ public static OperatorMatcher specifyOperatorMatcher(long... userIds) {
8585
return new OperatorMatcher("def run(content) {return [" + userIdsStr + "];}", STATE_SPECIFY);
8686
}
8787

88+
/**
89+
* 指定操作者匹配器
90+
*
91+
* @param userIds 用户ids
92+
* @return 操作者匹配器
93+
*/
94+
public static OperatorMatcher specifyOperatorMatcher(List<Long> userIds) {
95+
String userIdsStr = userIds.stream().map(String::valueOf).collect(Collectors.joining(","));
96+
return new OperatorMatcher("def run(content) {return [" + userIdsStr + "];}", STATE_SPECIFY);
97+
}
98+
8899
/**
89100
* 创建者操作者匹配器
90101
*

springboot-starter-flow/src/main/java/com/codingapi/springboot/flow/service/FlowDirectionService.java

+1-6
Original file line numberDiff line numberDiff line change
@@ -81,12 +81,7 @@ public void verifyFlowSourceDirection() {
8181
*/
8282
public boolean hasCurrentFlowNodeIsDone() {
8383
// 会签下所有人尚未提交时,不执行下一节点
84-
boolean allDone = historyRecords.stream().filter(item -> !item.isTransfer()).allMatch(FlowRecord::isDone);
85-
if (!allDone) {
86-
// 流程尚未审批结束直接退出
87-
return true;
88-
}
89-
return false;
84+
return historyRecords.stream().filter(item -> !item.isTransfer()).allMatch(FlowRecord::isDone);
9085
}
9186

9287

springboot-starter-flow/src/main/java/com/codingapi/springboot/flow/service/impl/FlowSubmitService.java

+2-2
Original file line numberDiff line numberDiff line change
@@ -98,8 +98,8 @@ public FlowResult submitFlow(long recordId, IFlowOperator currentOperator, IBind
9898

9999
// 判断流程是否结束(会签时需要所有人都通过)
100100
if (flowNode.isSign()) {
101-
boolean next = flowDirectionService.hasCurrentFlowNodeIsDone();
102-
if (next) {
101+
boolean isDone = flowDirectionService.hasCurrentFlowNodeIsDone();
102+
if (!isDone) {
103103
List<FlowRecord> todoRecords = historyRecords.stream().filter(FlowRecord::isTodo).collect(Collectors.toList());
104104
return new FlowResult(flowWork, todoRecords);
105105
}

springboot-starter-flow/src/main/java/com/codingapi/springboot/flow/service/impl/FlowTrySubmitService.java

+8-2
Original file line numberDiff line numberDiff line change
@@ -108,13 +108,19 @@ private FlowSubmitResult trySubmitFlow(FlowWork flowWork, FlowNode flowNode, Flo
108108
} else {
109109
// copy 流程数据防止影响原有数据
110110
historyRecords = flowRecordRepository.findFlowRecordByPreId(flowRecord.getPreId()).stream().map(FlowRecord::copy).collect(Collectors.toList());
111+
// 更新当前流程记录, 由于try测试过程中没有对数据落库,所以这里需要手动更新
112+
for(FlowRecord record : historyRecords){
113+
if(record.getId() == flowRecord.getId()){
114+
record.submitRecord(currentOperator, snapshot, opinion, flowSourceDirection);
115+
}
116+
}
111117
}
112118
flowDirectionService.bindHistoryRecords(historyRecords);
113119

114120
// 判断流程是否结束(会签时需要所有人都通过)
115121
if (flowNode.isSign()) {
116-
boolean next = flowDirectionService.hasCurrentFlowNodeIsDone();
117-
if (next) {
122+
boolean isDone = flowDirectionService.hasCurrentFlowNodeIsDone();
123+
if (!isDone) {
118124
List<FlowRecord> todoRecords = historyRecords.stream().filter(FlowRecord::isTodo).collect(Collectors.toList());
119125
return new FlowSubmitResult(flowWork, flowNode, todoRecords.stream().map(FlowRecord::getCurrentOperator).collect(Collectors.toList()));
120126
}

springboot-starter-flow/src/test/java/com/codingapi/springboot/flow/test/SignTest.java

+141
Original file line numberDiff line numberDiff line change
@@ -7,14 +7,18 @@
77
import com.codingapi.springboot.flow.em.ApprovalType;
88
import com.codingapi.springboot.flow.flow.Leave;
99
import com.codingapi.springboot.flow.matcher.OperatorMatcher;
10+
import com.codingapi.springboot.flow.pojo.FlowSubmitResult;
1011
import com.codingapi.springboot.flow.record.FlowRecord;
1112
import com.codingapi.springboot.flow.repository.*;
1213
import com.codingapi.springboot.flow.service.FlowService;
14+
import com.codingapi.springboot.flow.user.IFlowOperator;
1315
import com.codingapi.springboot.flow.user.User;
1416
import org.junit.jupiter.api.Test;
1517
import org.springframework.data.domain.PageRequest;
1618

19+
import java.util.ArrayList;
1720
import java.util.List;
21+
import java.util.stream.Collectors;
1822

1923
import static org.junit.jupiter.api.Assertions.assertEquals;
2024
import static org.junit.jupiter.api.Assertions.assertTrue;
@@ -403,4 +407,141 @@ void signRejectTest(){
403407
assertEquals(12, snapshots.size());
404408

405409
}
410+
411+
412+
413+
/**
414+
* 多人会签trySubmit测试
415+
*/
416+
@Test
417+
void signTrySubmitTest(){
418+
PageRequest pageRequest = PageRequest.of(0, 1000);
419+
420+
User caocao = new User("曹操");
421+
userRepository.save(caocao);
422+
User lvBu = new User("吕布");
423+
userRepository.save(lvBu);
424+
User zhaoYun = new User("赵云");
425+
userRepository.save(zhaoYun);
426+
427+
User user = new User("张飞");
428+
userRepository.save(user);
429+
430+
User dept = new User("刘备");
431+
userRepository.save(dept);
432+
433+
User boss = new User("诸葛亮");
434+
userRepository.save(boss);
435+
436+
List<User> signUsers = new ArrayList<>();
437+
signUsers.add(dept);
438+
signUsers.add(caocao);
439+
signUsers.add(lvBu);
440+
signUsers.add(zhaoYun);
441+
442+
FlowWork flowWork = FlowWorkBuilder.builder(user)
443+
.title("请假流程")
444+
.nodes()
445+
.node("开始节点", "start", "default", ApprovalType.UN_SIGN, OperatorMatcher.anyOperatorMatcher())
446+
.node("部门领导审批", "dept", "default", ApprovalType.SIGN, OperatorMatcher.specifyOperatorMatcher(signUsers.stream().map(User::getUserId).collect(Collectors.toList())))
447+
.node("总经理审批", "manager", "default", ApprovalType.UN_SIGN,OperatorMatcher.specifyOperatorMatcher(boss.getUserId()) )
448+
.node("结束节点", "over", "default", ApprovalType.UN_SIGN, OperatorMatcher.anyOperatorMatcher())
449+
.relations()
450+
.relation("部门领导审批", "start", "dept")
451+
.relation("总经理审批", "dept", "manager")
452+
.relation("结束节点", "manager", "over")
453+
.build();
454+
455+
flowWorkRepository.save(flowWork);
456+
457+
String workCode = flowWork.getCode();
458+
459+
Leave leave = new Leave("我要出去看看");
460+
leaveRepository.save(leave);
461+
462+
// 创建流程
463+
flowService.startFlow(workCode, user, leave, "发起流程");
464+
465+
// 查看我的待办
466+
List<FlowRecord> userTodos = flowRecordRepository.findTodoByOperatorId(user.getUserId(), pageRequest).getContent();
467+
assertEquals(1, userTodos.size());
468+
469+
// 提交流程
470+
FlowRecord userTodo = userTodos.get(0);
471+
472+
// 验证会签的人员
473+
FlowSubmitResult submitResult = flowService.trySubmitFlow(userTodo.getId(), user, leave, Opinion.pass("用户同意"));
474+
List<? extends IFlowOperator> operators = submitResult.getOperators();
475+
assertEquals(signUsers.size(), operators.size());
476+
477+
flowService.submitFlow(userTodo.getId(), user, leave, Opinion.pass("用户同意").specify(dept.getUserId()));
478+
479+
// 查看部门经理的待办
480+
List<FlowRecord> deptTodos = flowRecordRepository.findTodoByOperatorId(dept.getUserId(), pageRequest).getContent();
481+
assertEquals(1, deptTodos.size());
482+
483+
// 提交部门经理的审批
484+
FlowRecord deptTodo = deptTodos.get(0);
485+
486+
// 验证会签的人员
487+
submitResult = flowService.trySubmitFlow(deptTodo.getId(), dept, leave, Opinion.pass("用户同意"));
488+
operators = submitResult.getOperators();
489+
assertEquals(1, operators.size());
490+
assertEquals(boss.getName(), operators.get(0).getName());
491+
492+
flowService.submitFlow(deptTodo.getId(), dept, leave, Opinion.pass("刘备同意"));
493+
494+
// 查看总经理的待办
495+
List<FlowRecord> bossTodos = flowRecordRepository.findTodoByOperatorId(boss.getUserId(), pageRequest).getContent();
496+
assertEquals(1, bossTodos.size());
497+
498+
// // 查看部门经理 吕布 的待办
499+
// List<FlowRecord> lvbuTodos = flowRecordRepository.findTodoByOperatorId(lvBu.getUserId(), pageRequest).getContent();
500+
// assertEquals(1, lvbuTodos.size());
501+
//
502+
// // 提交部门经理 吕布 的审批
503+
// FlowRecord lvbuTodo = lvbuTodos.get(0);
504+
// flowService.submitFlow(lvbuTodo.getId(), lvBu, leave, Opinion.pass("吕布同意"));
505+
//
506+
//
507+
// // 查看部门经理 赵云 的待办
508+
// List<FlowRecord> zhaoYunTodos = flowRecordRepository.findTodoByOperatorId(zhaoYun.getUserId(), pageRequest).getContent();
509+
// assertEquals(1, zhaoYunTodos.size());
510+
//
511+
// // 提交部门经理 赵云 的审批
512+
// FlowRecord zhaoYunTodo = zhaoYunTodos.get(0);
513+
// flowService.submitFlow(zhaoYunTodo.getId(), zhaoYun, leave, Opinion.pass("赵云同意"));
514+
//
515+
//
516+
// // 查看部门经理 曹操 的待办
517+
// List<FlowRecord> caocaoTodos = flowRecordRepository.findTodoByOperatorId(caocao.getUserId(), pageRequest).getContent();
518+
// assertEquals(1, caocaoTodos.size());
519+
//
520+
// // 提交部门经理 曹操 的审批
521+
// FlowRecord caocaoTodo = caocaoTodos.get(0);
522+
// flowService.submitFlow(caocaoTodo.getId(), caocao, leave, Opinion.pass("曹操同意"));
523+
//
524+
// bossTodos = flowRecordRepository.findTodoByOperatorId(boss.getUserId(), pageRequest).getContent();
525+
// assertEquals(1, bossTodos.size());
526+
527+
// 提交总经理的审批
528+
FlowRecord bossTodo = bossTodos.get(0);
529+
flowService.submitFlow(bossTodo.getId(), boss, leave, Opinion.pass("同意"));
530+
531+
// 查看所有流程
532+
List<FlowRecord> records = flowRecordRepository.findAll(pageRequest).getContent();
533+
assertEquals(3, records.size());
534+
535+
userTodos = flowRecordRepository.findTodoByOperatorId(user.getUserId(), pageRequest).getContent();
536+
assertEquals(0, userTodos.size());
537+
538+
records = flowRecordRepository.findAll(pageRequest).getContent();
539+
assertEquals(3, records.size());
540+
// 查看所有流程是否都已经结束
541+
assertTrue(records.stream().allMatch(FlowRecord::isFinish));
542+
543+
List<BindDataSnapshot> snapshots = flowBindDataRepository.findAll();
544+
assertEquals(4, snapshots.size());
545+
546+
}
406547
}

springboot-starter-security/pom.xml

+1-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@
66
<parent>
77
<artifactId>springboot-parent</artifactId>
88
<groupId>com.codingapi.springboot</groupId>
9-
<version>2.9.8</version>
9+
<version>2.9.9</version>
1010
</parent>
1111

1212
<artifactId>springboot-starter-security</artifactId>

springboot-starter/pom.xml

+1-1
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@
55
<parent>
66
<groupId>com.codingapi.springboot</groupId>
77
<artifactId>springboot-parent</artifactId>
8-
<version>2.9.8</version>
8+
<version>2.9.9</version>
99
</parent>
1010
<artifactId>springboot-starter</artifactId>
1111

0 commit comments

Comments
 (0)