package com.ruoyi.ai.assistant;
|
|
import com.alibaba.fastjson2.JSON;
|
import com.ruoyi.ai.tools.ApproveTodoTools;
|
import org.springframework.stereotype.Component;
|
import org.springframework.util.StringUtils;
|
|
import java.math.BigDecimal;
|
import java.util.LinkedHashMap;
|
import java.util.Map;
|
import java.util.regex.Matcher;
|
import java.util.regex.Pattern;
|
|
@Component
|
public class ApproveTodoIntentExecutor {
|
|
private static final Pattern APPROVE_ID_PATTERN = Pattern.compile("\\b[A-Za-z]*\\d{8,}\\b");
|
private static final Pattern LIMIT_PATTERN = Pattern.compile("(前|最近)?(\\d{1,2})条");
|
private static final Pattern DATE_PATTERN = Pattern.compile("(\\d{4}-\\d{2}-\\d{2})");
|
private static final Pattern NUMBER_PATTERN = Pattern.compile("(\\d+(?:\\.\\d+)?)");
|
|
private final ApproveTodoTools approveTodoTools;
|
|
public ApproveTodoIntentExecutor(ApproveTodoTools approveTodoTools) {
|
this.approveTodoTools = approveTodoTools;
|
}
|
|
public String tryExecute(String memoryId, String message) {
|
if (!StringUtils.hasText(message)) {
|
return null;
|
}
|
|
String text = message.trim();
|
String approveId = extractApproveId(text);
|
|
if (containsAny(text, "统计", "分析", "图表", "趋势", "占比")) {
|
return approveTodoTools.getTodoStats(
|
memoryId,
|
extractStartDate(text),
|
extractEndDate(text),
|
extractTimeRange(text)
|
);
|
}
|
if (containsAny(text, "流转", "进度", "节点", "日志")) {
|
return StringUtils.hasText(approveId)
|
? approveTodoTools.getTodoProgress(memoryId, approveId)
|
: missingApproveId("todo_progress", "查询审批进度需要提供流程编号。");
|
}
|
if (containsAny(text, "详情", "明细") && !containsAny(text, "列表")) {
|
return StringUtils.hasText(approveId)
|
? approveTodoTools.getTodoDetail(memoryId, approveId)
|
: missingApproveId("todo_detail", "查询审批详情需要提供流程编号。");
|
}
|
if (containsAny(text, "取消审核", "撤销审核", "回退审核")) {
|
return StringUtils.hasText(approveId)
|
? approveTodoTools.cancelReviewTodo(memoryId, approveId, extractTail(text, "原因"))
|
: missingApproveId("cancel_review_action", "取消审核需要提供流程编号。");
|
}
|
if (containsAny(text, "删除")) {
|
return StringUtils.hasText(approveId)
|
? approveTodoTools.deleteTodo(memoryId, approveId)
|
: missingApproveId("delete_action", "删除审批单需要提供流程编号。");
|
}
|
if (containsAny(text, "驳回", "拒绝")) {
|
return StringUtils.hasText(approveId)
|
? approveTodoTools.reviewTodo(memoryId, approveId, "reject", extractTail(text, "原因"))
|
: missingApproveId("review_action", "驳回审批需要提供流程编号。");
|
}
|
if (containsAny(text, "审核通过", "审批通过", "通过审批", "同意审批", "审批同意")) {
|
return StringUtils.hasText(approveId)
|
? approveTodoTools.reviewTodo(memoryId, approveId, "approve", extractTail(text, "备注"))
|
: missingApproveId("review_action", "审批通过需要提供流程编号。");
|
}
|
if (StringUtils.hasText(approveId)
|
&& containsAny(text, "通过", "同意")
|
&& !containsAny(text, "未通过", "通过率", "审批通过率", "审核通过率")) {
|
return approveTodoTools.reviewTodo(memoryId, approveId, "approve", extractTail(text, "备注"));
|
}
|
if (containsAny(text, "修改")) {
|
return StringUtils.hasText(approveId)
|
? approveTodoTools.updateTodo(
|
memoryId,
|
approveId,
|
extractValue(text, "标题"),
|
extractDateValue(text, "开始日期"),
|
extractDateValue(text, "结束日期"),
|
extractBigDecimalValue(text, "金额"),
|
extractValue(text, "地点"),
|
extractIntegerValue(text, "类型"),
|
extractValue(text, "备注"))
|
: missingApproveId("update_action", "修改审批单需要提供流程编号。");
|
}
|
if (containsAny(text, "列表", "待办", "查询审批")) {
|
return approveTodoTools.listTodos(
|
memoryId,
|
extractStatus(text),
|
extractApproveType(text),
|
extractKeyword(text),
|
extractLimit(text));
|
}
|
return null;
|
}
|
|
private boolean containsAny(String text, String... keywords) {
|
for (String keyword : keywords) {
|
if (text.contains(keyword)) {
|
return true;
|
}
|
}
|
return false;
|
}
|
|
private String extractApproveId(String text) {
|
Matcher matcher = APPROVE_ID_PATTERN.matcher(text);
|
return matcher.find() ? matcher.group() : null;
|
}
|
|
private Integer extractLimit(String text) {
|
Matcher matcher = LIMIT_PATTERN.matcher(text);
|
return matcher.find() ? Integer.parseInt(matcher.group(2)) : 10;
|
}
|
|
private String extractStatus(String text) {
|
if (containsAny(text, "待审核", "待审批")) {
|
return "pending";
|
}
|
if (containsAny(text, "审核中")) {
|
return "processing";
|
}
|
if (containsAny(text, "已通过", "审核完成")) {
|
return "approved";
|
}
|
if (containsAny(text, "未通过", "驳回")) {
|
return "rejected";
|
}
|
if (containsAny(text, "重新提交")) {
|
return "resubmitted";
|
}
|
return "all";
|
}
|
|
private Integer extractApproveType(String text) {
|
if (text.contains("公出")) {
|
return 1;
|
}
|
if (text.contains("请假")) {
|
return 2;
|
}
|
if (text.contains("出差")) {
|
return 3;
|
}
|
if (text.contains("报销")) {
|
return 4;
|
}
|
if (text.contains("采购")) {
|
return 5;
|
}
|
if (text.contains("报价")) {
|
return 6;
|
}
|
if (text.contains("发货")) {
|
return 7;
|
}
|
if (text.contains("危险作业")) {
|
return 8;
|
}
|
return null;
|
}
|
|
private String extractKeyword(String text) {
|
String cleaned = text
|
.replace("查询", "")
|
.replace("审批", "")
|
.replace("待办", "")
|
.replace("列表", "")
|
.replace("前10条", "")
|
.replace("最近10条", "")
|
.trim();
|
return cleaned.length() >= 2 ? cleaned : null;
|
}
|
|
private String extractValue(String text, String fieldName) {
|
Pattern pattern = Pattern.compile(fieldName + "(改为|修改为|是)?[::]?[\\s]*([^,,。;;\\s]+)");
|
Matcher matcher = pattern.matcher(text);
|
return matcher.find() ? matcher.group(2) : null;
|
}
|
|
private String extractDateValue(String text, String fieldName) {
|
int index = text.indexOf(fieldName);
|
if (index < 0) {
|
return null;
|
}
|
Matcher matcher = DATE_PATTERN.matcher(text.substring(index));
|
return matcher.find() ? matcher.group(1) : null;
|
}
|
|
private String extractStartDate(String text) {
|
Matcher matcher = DATE_PATTERN.matcher(text);
|
return matcher.find() ? matcher.group(1) : null;
|
}
|
|
private String extractEndDate(String text) {
|
Matcher matcher = DATE_PATTERN.matcher(text);
|
if (!matcher.find()) {
|
return null;
|
}
|
return matcher.find() ? matcher.group(1) : null;
|
}
|
|
private String extractTimeRange(String text) {
|
if (containsAny(text, "今天", "昨日", "昨天", "本周", "上周", "本月", "上月", "本年", "今年", "去年")) {
|
return text;
|
}
|
if (Pattern.compile("近\\d+(天|周|个月|月|年)").matcher(text).find()) {
|
return text;
|
}
|
if (Pattern.compile("最近\\d+(天|周|个月|月|年)").matcher(text).find()) {
|
return text;
|
}
|
if (text.contains("到") || text.contains("至")) {
|
return text;
|
}
|
return null;
|
}
|
|
private Integer extractIntegerValue(String text, String fieldName) {
|
if (!text.contains(fieldName)) {
|
return null;
|
}
|
Matcher matcher = Pattern.compile(fieldName + "(改为|修改为|是)?[::]?[\\s]*(\\d{1,2})").matcher(text);
|
return matcher.find() ? Integer.parseInt(matcher.group(2)) : null;
|
}
|
|
private BigDecimal extractBigDecimalValue(String text, String fieldName) {
|
int index = text.indexOf(fieldName);
|
if (index < 0) {
|
return null;
|
}
|
Matcher matcher = NUMBER_PATTERN.matcher(text.substring(index));
|
return matcher.find() ? new BigDecimal(matcher.group(1)) : null;
|
}
|
|
private String extractTail(String text, String key) {
|
Pattern pattern = Pattern.compile(key + "(是|为)?[::]?[\\s]*(.+)");
|
Matcher matcher = pattern.matcher(text);
|
return matcher.find() ? matcher.group(2).trim() : null;
|
}
|
|
private String missingApproveId(String type, String description) {
|
Map<String, Object> result = new LinkedHashMap<>();
|
result.put("success", false);
|
result.put("type", type);
|
result.put("description", description);
|
result.put("summary", Map.of());
|
result.put("data", Map.of());
|
result.put("charts", Map.of());
|
return JSON.toJSONString(result);
|
}
|
}
|