refactor(bpm): 重构工单跟踪记录相关功能

-移除 BpmOAWorkOrderTrackDO 中的操作类型字段
- 更新相关 VO 和 DTO,移除操作类型相关代码
- 修改工单创建和跟踪记录创建逻辑,将操作类型合并到内容中
- 新增地址逆解析相关功能
This commit is contained in:
aikai 2025-06-30 11:22:45 +08:00
parent 68d6971fda
commit 1c6f687965
11 changed files with 127 additions and 113 deletions

View File

@ -0,0 +1,82 @@
package cn.iocoder.yudao.framework.common.util.address;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
public class AddressUtil {
// 替换成您在天地图官网申请的密钥
private static final String API_KEY = "e11694af0e347f991a0b18f10f2491d3";
public static void main(String[] args) {
// 示例经纬度深圳腾讯大厦
double longitude = 115.43835;
double latitude = 28.200279;
// 35.88052,114.8731
try {
String result = reverseGeocode(longitude, latitude);
System.out.println("逆地理编码结果:");
System.out.println(result);
} catch (Exception e) {
System.err.println("逆地理编码失败:");
e.printStackTrace();
}
}
public static String reverseGeocode(double longitude, double latitude) throws Exception {
// 1. 构建请求参数注意使用双引号
String postStr = String.format("{\"lon\":%f,\"lat\":%f,\"ver\":2}", longitude, latitude);
// 2. URL编码参数
String encodedPostStr = URLEncoder.encode(postStr, StandardCharsets.UTF_8.name());
// 3. 构建完整URL
String urlStr = "http://api.tianditu.gov.cn/geocoder?postStr=" + encodedPostStr
+ "&type=geocode&tk=" + API_KEY;
// 4. 创建HTTP连接
URL url = new URL(urlStr);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
conn.setRequestMethod("GET");
// 5. 设置请求头模拟浏览器访问
conn.setRequestProperty("User-Agent", "Mozilla/5.0");
conn.setRequestProperty("Accept", "application/json");
// 6. 获取响应
int responseCode = conn.getResponseCode();
if (responseCode == HttpURLConnection.HTTP_OK) {
// 读取成功响应
try (BufferedReader reader = new BufferedReader(
new InputStreamReader(conn.getInputStream(), StandardCharsets.UTF_8))) {
StringBuilder response = new StringBuilder();
String line;
while ((line = reader.readLine()) != null) {
response.append(line);
}
return response.toString();
}
} else {
// 读取错误信息
try (BufferedReader errorReader = new BufferedReader(
new InputStreamReader(conn.getErrorStream(), StandardCharsets.UTF_8))) {
StringBuilder errorResponse = new StringBuilder();
String line;
while ((line = errorReader.readLine()) != null) {
errorResponse.append(line);
}
throw new RuntimeException("API请求失败: HTTP " + responseCode
+ "\n错误详情: " + errorResponse.toString());
}
}
}
}

View File

@ -1,71 +0,0 @@
package cn.iocoder.yudao.module.bpm.dal.dataobject.oa;
import cn.iocoder.yudao.framework.mybatis.core.dataobject.BaseDO;
import cn.iocoder.yudao.framework.mybatis.core.type.JsonLongSetTypeHandler;
import com.baomidou.mybatisplus.annotation.KeySequence;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.*;
/**
* BPM OA 工单跟踪记录 DO
*
* @author 系统
*/
@TableName(value = "bpm_oa_work_order_track", autoResultMap = true)
@KeySequence("bpm_oa_work_order_track_seq") // 用于 OraclePostgreSQLKingbaseDB2H2 数据库的主键自增如果是 MySQL 等数据库可不写
@Data
@EqualsAndHashCode(callSuper = true)
@ToString(callSuper = true)
@Builder
@NoArgsConstructor
@AllArgsConstructor
public class BpmOAWorkOrderTrackDO extends BaseDO {
/**
* 跟踪记录ID
*/
@TableId
private Long id;
/**
* 工单ID
*/
private Long workOrderId;
/**
* 操作人ID
*/
private Long operatorId;
/**
* 操作人姓名
*/
private String operatorName;
/**
* 操作类型
*
* 枚举值
* - CREATE: 创建工单
* - ASSIGN: 分配工单
* - PROCESS: 处理中
* - COMPLETE: 完成工单
* - CANCEL: 取消工单
* - COMMENT: 添加备注
*/
private String operationType;
/**
* 操作内容/备注
*/
private String content;
/**
* 附件文件列表JSON格式
*/
@TableField(typeHandler = JsonLongSetTypeHandler.class)
private String attachments;
}

View File

@ -124,5 +124,9 @@ public interface ErrorCodeConstants {
= new ErrorCode(1_009_012_002, "流程审批中或已通过当月不可重复申请");
ErrorCode THE_WORK_ORDER_RULE_TYPE_ALREADY_EXISTS_PLEASE_DO_NOT_ADD_IT_REPEATEDLY
= new ErrorCode(1_009_013_001, "工单规则类型已存在,请勿重复添加");
ErrorCode BPM_SYSTEM_BUG = new ErrorCode(1_009_012_001, "系统问题,请联系管理员");
}

View File

@ -27,7 +27,4 @@ public class BpmOAWorkOrderTrackInfo {
@Schema(description = "操作时间")
private String trackTime;
@Schema(description = "操作类型")
private String operationType;
}
}

View File

@ -4,7 +4,6 @@ import cn.iocoder.yudao.framework.common.pojo.PageParam;
import io.swagger.v3.oas.annotations.media.Schema;
import lombok.Data;
import javax.validation.constraints.NotEmpty;
import javax.validation.constraints.NotNull;
@Data
@ -14,7 +13,4 @@ public class BpmOAWorkOrderTrackReqDTO extends PageParam {
@NotNull(message = "工单ID不能为空")
private Long workOrderId;
@Schema(description = "操作类型", requiredMode = Schema.RequiredMode.REQUIRED, example = "PROCESS")
private String operationType;
}

View File

@ -14,12 +14,8 @@ public class BpmOAWorkOrderTrackReqVO {
@NotNull(message = "工单ID不能为空")
private Long workOrderId;
@Schema(description = "操作类型", requiredMode = Schema.RequiredMode.REQUIRED, example = "PROCESS")
@NotEmpty(message = "操作类型不能为空")
private String operationType;
@Schema(description = "操作内容", requiredMode = Schema.RequiredMode.REQUIRED, example = "已开始处理该工单,预计今天下午完成")
@NotEmpty(message = "操作内容不能为空")
private String content;
}
}

View File

@ -28,44 +28,31 @@ public class BpmOAWorkOrderTrackDO extends BaseDO {
*/
@TableId
private Long id;
/**
* 工单ID
*/
private Long workOrderId;
/**
* 操作人ID
*/
private Long operatorId;
/**
* 操作人姓名
*/
private String operatorName;
/**
* 操作类型
*
* 枚举值
* - CREATE: 创建工单
* - ASSIGN: 分配工单
* - PROCESS: 处理中
* - COMPLETE: 完成工单
* - CANCEL: 取消工单
* - COMMENT: 添加备注
*/
private String operationType;
/**
* 操作内容/备注
*/
private String content;
/**
* 附件文件列表JSON格式
*/
@TableField(typeHandler = JsonLongSetTypeHandler.class)
private String attachments;
}
}

View File

@ -27,6 +27,7 @@ import java.util.stream.Collectors;
import static cn.iocoder.yudao.framework.common.exception.util.ServiceExceptionUtil.exception;
import static cn.iocoder.yudao.framework.common.util.collection.CollectionUtils.convertMap;
import static cn.iocoder.yudao.module.bpm.enums.ErrorCodeConstants.OA_WORK_TASK_NOT_EXISTS;
import static cn.iocoder.yudao.module.bpm.enums.ErrorCodeConstants.THE_WORK_ORDER_RULE_TYPE_ALREADY_EXISTS_PLEASE_DO_NOT_ADD_IT_REPEATEDLY;
/**
* BPM OA 工单分配规则 Service 实现类
@ -57,6 +58,12 @@ public class BpmOAWorkOrderAssignRuleServiceImpl implements BpmOAWorkOrderAssign
public Long createWorkOrderAssignRule(BpmOAWorkOrderAssignRuleSaveReqVO createReqVO) {
// 插入
BpmOAWorkOrderAssignRuleDO workOrderAssignRule = BeanUtils.toBean(createReqVO, BpmOAWorkOrderAssignRuleDO.class);
// -- 判断系统中是否已经存在该规则 - 如果存在提示已存在 - 请勿重复添加
BpmOAWorkOrderAssignRuleDO bpmOAWorkOrderAssignRuleDO = workOrderAssignRuleMapper.selectOne(new LambdaQueryWrapperX<BpmOAWorkOrderAssignRuleDO>()
.eq(BpmOAWorkOrderAssignRuleDO::getWorkOrderType, workOrderAssignRule.getWorkOrderType()));
if (bpmOAWorkOrderAssignRuleDO != null) {
throw exception(THE_WORK_ORDER_RULE_TYPE_ALREADY_EXISTS_PLEASE_DO_NOT_ADD_IT_REPEATEDLY);
}
workOrderAssignRuleMapper.insert(workOrderAssignRule);
// 返回

View File

@ -1,6 +1,5 @@
package cn.iocoder.yudao.module.bpm.service.oa;
import cn.hutool.core.util.StrUtil;
import cn.iocoder.yudao.framework.common.pojo.PageParam;
import cn.iocoder.yudao.framework.common.pojo.PageResult;
import cn.iocoder.yudao.framework.common.pojo.UploadUserFile;
@ -112,7 +111,7 @@ public class BpmOAWorkOrderServiceImpl extends BpmOABaseService implements BpmOA
workOrderMapper.updateById(new BpmOAWorkOrderDO().setId(workOrder.getId()).setProcessInstanceId(processInstanceId));
// 创建初始跟踪记录
createTrackRecord(workOrder.getId(), userId, userRespDTO.getNickname(), "CREATE", "创建工单", null);
createTrackRecord(workOrder.getId(), userId, userRespDTO.getNickname(), "创建工单", null);
List<UploadUserFile> fileItems = createReqVO.getFileItems();
//这里的逻辑如果fileItems不为空且有数据那么说明是上传了附件的则需要更工作流文件表对应的实例Id
@ -148,14 +147,14 @@ public class BpmOAWorkOrderServiceImpl extends BpmOABaseService implements BpmOA
// 创建分配跟踪记录
AdminUserRespDTO assigneeUser = userApi.getUser(assigneeUserId).getCheckedData();
createTrackRecord(id, assigneeUserId, assigneeUser.getNickname(), "ASSIGN", "工单已分配给:" + assigneeUser.getNickname(), null);
createTrackRecord(id, assigneeUserId, assigneeUser.getNickname(), "工单已分配给:" + assigneeUser.getNickname(), null);
}
@Override
public void addTrackInfo(Long userId, BpmOAWorkOrderTrackReqVO trackReqVO) {
AdminUserRespDTO userRespDTO = userApi.getUser(userId).getCheckedData();
createTrackRecord(trackReqVO.getWorkOrderId(), userId, userRespDTO.getNickname(),
trackReqVO.getOperationType(), trackReqVO.getContent(), null);
createTrackRecord(trackReqVO.getWorkOrderId(), userId, userRespDTO.getNickname()
, trackReqVO.getContent(), null);
}
@Override
@ -253,20 +252,18 @@ public class BpmOAWorkOrderServiceImpl extends BpmOABaseService implements BpmOA
public PageResult<BpmOAWorkOrderTrackInfo> getTrackPage(BpmOAWorkOrderTrackReqDTO dto) {
PageResult<BpmOAWorkOrderTrackDO> pageResult = trackMapper.selectPage(new PageParam().setPageSize(dto.getPageSize()).setPageNo(dto.getPageNo()),
new LambdaQueryWrapper<BpmOAWorkOrderTrackDO>()
.eq(dto.getWorkOrderId() != null, BpmOAWorkOrderTrackDO::getWorkOrderId, dto.getWorkOrderId())
.eq(StrUtil.isNotEmpty(dto.getOperationType()), BpmOAWorkOrderTrackDO::getOperationType, dto.getOperationType()));
.eq(dto.getWorkOrderId() != null, BpmOAWorkOrderTrackDO::getWorkOrderId, dto.getWorkOrderId()));
return new PageResult<>(pageResult.getList().stream().map(this::convertToTrackInfo).collect(Collectors.toList()), pageResult.getTotal());
}
/**
* 创建跟踪记录
*/
private void createTrackRecord(Long workOrderId, Long operatorId, String operatorName, String operationType, String content, String attachments) {
private void createTrackRecord(Long workOrderId, Long operatorId, String operatorName, String content, String attachments) {
BpmOAWorkOrderTrackDO track = BpmOAWorkOrderTrackDO.builder()
.workOrderId(workOrderId)
.operatorId(operatorId)
.operatorName(operatorName)
.operationType(operationType)
.content(content)
.attachments(attachments)
.build();
@ -383,7 +380,6 @@ public class BpmOAWorkOrderServiceImpl extends BpmOABaseService implements BpmOA
trackInfo.setOperatorId(trackDO.getOperatorId());
trackInfo.setOperatorName(trackDO.getOperatorName());
trackInfo.setContent(trackDO.getContent());
trackInfo.setOperationType(trackDO.getOperationType());
trackInfo.setTrackTime(trackDO.getCreateTime().format(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
return trackInfo;

View File

@ -1,9 +1,12 @@
package cn.iocoder.yudao.module.system.controller.admin.attendance;
import cn.iocoder.yudao.framework.common.pojo.CommonResult;
import cn.iocoder.yudao.framework.common.util.address.AddressUtil;
import cn.iocoder.yudao.module.system.controller.admin.attendance.dto.*;
import cn.iocoder.yudao.module.system.controller.admin.attendance.vo.*;
import cn.iocoder.yudao.module.system.service.attendance.AttendanceService;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONObject;
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.tags.Tag;
import org.springframework.validation.annotation.Validated;
@ -119,4 +122,20 @@ public class AttendanceController {
attendanceService.generateHolidayToRedis(year);
return success("ok");
}
@GetMapping("/addressInverseResolution")
@Operation(summary = "地址逆解析")
@PermitAll
public CommonResult<?> addressInverseResolution(@RequestParam(name = "longitude") double longitude, @RequestParam(name = "latitude") double latitude) {
String result = "";
try {
result = AddressUtil.reverseGeocode(longitude, latitude);
} catch (Exception e) {
System.err.println("逆地理编码失败:");
e.printStackTrace();
}
JSONObject jsonObject = JSON.parseObject(result);
return success(jsonObject);
}
}

View File

@ -8,6 +8,7 @@ import cn.iocoder.yudao.module.system.controller.admin.attendance.vo.*;
import cn.iocoder.yudao.module.system.dal.dataobject.attendance.addressgroup.AttendanceAddressGroupItemDO;
import cn.iocoder.yudao.module.system.dal.dataobject.attendance.groupshiftitem.AttendanceGroupShiftItemDO;
import cn.iocoder.yudao.module.system.service.attendance.punch.dto.AttendanceOnTheDayDTO;
import com.google.gson.JsonObject;
import javax.servlet.http.HttpServletResponse;
import java.time.LocalDateTime;