Compare commits

..

73 Commits

Author SHA1 Message Date
0126d44761 ws注解放开 2025-10-27 20:42:03 +08:00
dbefd88e41 添加客户详情权限 2025-10-27 20:09:39 +08:00
9a3b7ebe54 添加审核 2025-10-27 20:00:56 +08:00
81be4a862c 10-27-添加审核完善 2025-10-27 19:57:35 +08:00
lg
43f2db9f7e 审核数据添加 2025-10-27 19:51:55 +08:00
abefa90408 10-27-添加审核完善 2025-10-27 19:14:24 +08:00
08f48b7817 10-27-添加审核 2025-10-27 18:45:49 +08:00
lcj
6b8ace60d4 车辆管理,修改材料 2025-10-27 17:10:41 +08:00
lg
b997dd5f00 详情权限取消 2025-10-27 15:35:49 +08:00
6174743858 Merge remote-tracking branch 'origin/dev' into dev 2025-10-27 15:25:19 +08:00
82d55d7188 10-27-修改bug 2025-10-27 15:25:06 +08:00
lg
aec5eacd0b 采购详情权限取消 2025-10-27 15:25:04 +08:00
zt
a320b85965 考勤机 2025-10-27 15:14:29 +08:00
lg
b61a7c153d 投标文件-项目类型中文返回 2025-10-27 14:44:50 +08:00
fb9b01cf34 修改物资跟踪管理台账查询列表修改 2025-10-27 14:27:11 +08:00
lg
32f134873a 采购合同金额字段 2025-10-27 11:37:41 +08:00
f4220be9d6 10-27-修改bug 2025-10-27 10:29:27 +08:00
lg
8252fd7216 标后分析返回对象增加字段 2025-10-27 09:44:11 +08:00
lg
57855f4307 bug修改 2025-10-25 22:18:10 +08:00
6784eafe6e 供应商-客户中间表引用表的新增修改删除修改 2025-10-25 22:17:26 +08:00
0b42c1d6a6 Merge remote-tracking branch 'origin/dev' into dev 2025-10-25 22:16:07 +08:00
4b37a7327f 10-25-修改 2025-10-25 22:16:00 +08:00
lg
0287f1e4ce bug修改 2025-10-25 21:58:47 +08:00
5d8af1cab8 10-25-供应商删除修改 2025-10-25 21:57:13 +08:00
123896f08b Merge remote-tracking branch 'origin/dev' into dev 2025-10-25 21:25:40 +08:00
a8a198b51f 10-25-增加校验 2025-10-25 21:25:33 +08:00
lg
f00b98714a Merge remote-tracking branch 'origin/dev' into dev 2025-10-25 21:24:39 +08:00
lg
4ff87f3996 bug修改 2025-10-25 21:23:58 +08:00
5f3ae0f9f1 10-25-供应商地域绑定及搜索 2025-10-25 21:22:36 +08:00
786c864a27 供应商-客户中间表引用表的新增修改删除修改 2025-10-25 21:21:48 +08:00
lg
c61e802b85 bug修改 2025-10-25 21:09:26 +08:00
lg
9a568799f4 bug修改 2025-10-25 21:05:26 +08:00
8aa38063bf 供应商-客户中间表引用表的新增修改删除 2025-10-25 20:58:07 +08:00
c4a11ec245 10-25-解除继承 2025-10-25 20:28:40 +08:00
lg
169b76589c bug修改 2025-10-25 20:23:02 +08:00
lg
199f51ea21 bug修改 2025-10-25 20:19:21 +08:00
lg
23572dfc07 bug修改 2025-10-25 20:14:03 +08:00
570b0ce316 10-25-供应商新增、删除添加校验 2025-10-25 20:11:14 +08:00
lg
f953a96c36 bug修改 2025-10-25 20:05:43 +08:00
zt
25c4eee464 bug 2025-10-25 20:01:28 +08:00
lg
b209ef1fab 中间表数据添加 2025-10-25 19:20:32 +08:00
lg
77e9f4d9a2 中间表数据添加 2025-10-25 19:18:09 +08:00
lg
e73c808bc3 xzd前缀添加 2025-10-25 17:21:16 +08:00
zt
edf0d1a5db 设计导出 2025-10-25 17:10:43 +08:00
lcj
cc23a308c1 修改配置,车辆管理 2025-10-25 17:01:15 +08:00
bc891327c9 10-25-字段调整 2025-10-25 16:51:17 +08:00
39bedfeb92 10-25-字段调整 2025-10-25 16:44:33 +08:00
56fc4ff83e 10-24-修复 2025-10-24 22:16:26 +08:00
524ed30728 Merge remote-tracking branch 'origin/dev' into dev 2025-10-24 22:16:13 +08:00
584304e744 供应商-客户中间表初始化 2025-10-24 22:07:16 +08:00
zt
56418600c5 1 2025-10-24 20:17:03 +08:00
40e57b18cb 10-24-修复 2025-10-24 20:05:45 +08:00
lg
ced6cb219c deptid添加 2025-10-24 20:01:03 +08:00
218ec5ea95 gps接口修改 2025-10-24 19:40:54 +08:00
zt
1c601bd68e 设计导出 2025-10-24 19:32:20 +08:00
lg
7d6eba719b 投标保证金收回 2025-10-24 17:50:15 +08:00
8cfc34dbcb Merge remote-tracking branch 'origin/dev' into dev 2025-10-24 17:46:29 +08:00
23a749973d 10-24-修复 2025-10-24 17:45:59 +08:00
4b96702dc9 成本预算添加部门id 2025-10-24 17:41:37 +08:00
a1af8711ef 添加id转name注解方法 2025-10-24 17:05:11 +08:00
9e8cff931b 10-24-修复 2025-10-24 17:00:15 +08:00
lg
5bccd71bdc 投标保证金缴纳 2025-10-24 16:59:24 +08:00
lg
544f35a601 投标管理修改 2025-10-24 16:04:38 +08:00
f920d4976e 10-24-修复 2025-10-24 15:22:31 +08:00
cdcd665d43 添加id转name注解方法 2025-10-24 11:55:19 +08:00
lg
08de61e455 trans添加客户供应商 2025-10-24 10:48:06 +08:00
lcj
025c3115b7 接入ai,识别 2025-10-24 09:23:40 +08:00
9e366554b7 10-23-修复 2025-10-23 22:35:04 +08:00
zt
d934abf0fe bug修改 2025-10-23 19:36:49 +08:00
lg
e16e9133e2 采购合同修改 2025-10-23 17:42:42 +08:00
d7854a35d7 10-23-修复 2025-10-23 17:36:00 +08:00
97e0dd467f Merge remote-tracking branch 'origin/dev' into dev 2025-10-23 17:24:08 +08:00
e58a99e696 10-23-修复 2025-10-23 17:24:00 +08:00
442 changed files with 12209 additions and 2360 deletions

View File

@ -36,6 +36,12 @@ snail-job:
--- # 数据源配置 --- # 数据源配置
spring: spring:
ai:
dashscope:
api-key: sk-8d8df92fcbac4bd2922edba30b0bb8fa
chat:
options:
model: qwen-plus
datasource: datasource:
type: com.zaxxer.hikari.HikariDataSource type: com.zaxxer.hikari.HikariDataSource
# 动态数据源文档 https://www.kancloud.cn/tracy5546/dynamic-datasource/content # 动态数据源文档 https://www.kancloud.cn/tracy5546/dynamic-datasource/content
@ -56,9 +62,9 @@ spring:
url: jdbc:mysql://192.168.110.2:13386/xinnengyuandev?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8 url: jdbc:mysql://192.168.110.2:13386/xinnengyuandev?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8
username: xinnengyuandev username: xinnengyuandev
password: StRWCZdZirysNSs2 password: StRWCZdZirysNSs2
# url: jdbc:mysql://192.168.110.2:13386/xinnengyuan?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8 # url: jdbc:mysql://192.168.110.2:13386/xinnengyuan?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8
# username: xinnengyuan # username: xinnengyuan
# password: mEZPC5Sdf3r2HENi # password: mEZPC5Sdf3r2HENi
# 从库数据源 # 从库数据源
slave: slave:
lazy: true lazy: true
@ -81,13 +87,13 @@ spring:
url: jdbc:mysql://192.168.110.2:13386/zmkgc?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true&nullCatalogMeansCurrent=true url: jdbc:mysql://192.168.110.2:13386/zmkgc?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true&nullCatalogMeansCurrent=true
username: zmkgc username: zmkgc
password: nWKDKRNRT48tFBdh password: nWKDKRNRT48tFBdh
# slave: # slave:
# lazy: true # lazy: true
# type: ${spring.datasource.type} # type: ${spring.datasource.type}
# driverClassName: com.mysql.cj.jdbc.Driver # driverClassName: com.mysql.cj.jdbc.Driver
# url: jdbc:mysql://192.168.110.2:13386/zmkgprod?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true&nullCatalogMeansCurrent=true # url: jdbc:mysql://192.168.110.2:13386/zmkgprod?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8&autoReconnect=true&rewriteBatchedStatements=true&allowPublicKeyRetrieval=true&nullCatalogMeansCurrent=true
# username: zmkgprod # username: zmkgprod
# password: MaY8nehwWkJriWPm # password: MaY8nehwWkJriWPm
# oracle: # oracle:
# type: ${spring.datasource.type} # type: ${spring.datasource.type}
# driverClassName: oracle.jdbc.OracleDriver # driverClassName: oracle.jdbc.OracleDriver

View File

@ -39,6 +39,12 @@ snail-job:
--- # 数据源配置 --- # 数据源配置
spring: spring:
ai:
dashscope:
api-key: xxx
chat:
options:
model: qwen-plus
datasource: datasource:
type: com.zaxxer.hikari.HikariDataSource type: com.zaxxer.hikari.HikariDataSource
# 动态数据源文档 https://www.kancloud.cn/tracy5546/dynamic-datasource/content # 动态数据源文档 https://www.kancloud.cn/tracy5546/dynamic-datasource/content
@ -315,8 +321,8 @@ ys7:
app-key: xxx app-key: xxx
app-secret: xxx app-secret: xxx
job: job:
capture-enabled: true # 控制是否启用萤石抓拍任务 capture-enabled: false # 控制是否启用萤石抓拍任务
device-sync-enabled: true # 控制是否同步萤石设备 device-sync-enabled: false # 控制是否同步萤石设备
# 斯巴达算法 # 斯巴达算法
sparta: sparta:
url: http://119.3.204.120:8040 url: http://119.3.204.120:8040

View File

@ -39,6 +39,12 @@ snail-job:
--- # 数据源配置 --- # 数据源配置
spring: spring:
ai:
dashscope:
api-key: xxx
chat:
options:
model: qwen-plus
datasource: datasource:
type: com.zaxxer.hikari.HikariDataSource type: com.zaxxer.hikari.HikariDataSource
# 动态数据源文档 https://www.kancloud.cn/tracy5546/dynamic-datasource/content # 动态数据源文档 https://www.kancloud.cn/tracy5546/dynamic-datasource/content

View File

@ -289,6 +289,8 @@ springdoc:
packages-to-scan: org.dromara.websocket packages-to-scan: org.dromara.websocket
- group: 27.新中大模块 - group: 27.新中大模块
packages-to-scan: org.dromara.xzd packages-to-scan: org.dromara.xzd
- group: 28.车辆模块
packages-to-scan: org.dromara.vehicle
# knife4j的增强配置不需要增强可以不配 # knife4j的增强配置不需要增强可以不配
knife4j: knife4j:
enable: true enable: true
@ -306,12 +308,12 @@ xss:
- /project/project - /project/project
- /xzd/contractDetails/** - /xzd/contractDetails/**
- /xzd/contractChange/** - /xzd/contractChange/**
- /comprehensive/csContractChange/** - /xzd/comprehensive/csContractChange/**
- /comprehensive/csContractInformation/** - /xzd/comprehensive/csContractInformation/**
- /hetongbiangeng/** - /xzd/hetongbiangeng/**
- /fenbaohetongbiangg/** - /xzd/fenbaohetongbiangg/**
- /fenbaohetongxinxi/** - /xzd/fenbaohetongxinxi/**
- /contractManagement/** - /xzd/contractManagement/**
# 全局线程池相关配置 # 全局线程池相关配置
# 如使用JDK21请直接使用虚拟线程 不要开启此配置 # 如使用JDK21请直接使用虚拟线程 不要开启此配置

View File

@ -29,6 +29,8 @@ import org.dromara.manager.ys7manager.Ys7Constant;
import org.dromara.manager.ys7manager.Ys7Manager; import org.dromara.manager.ys7manager.Ys7Manager;
import org.dromara.manager.ys7manager.vo.Ys7ResponseVo; import org.dromara.manager.ys7manager.vo.Ys7ResponseVo;
import org.dromara.other.domain.OthYs7Device; import org.dromara.other.domain.OthYs7Device;
import org.dromara.other.domain.dto.ys7deviceimg.OthYs7DeviceImgCreateByCapture;
import org.dromara.other.service.IOthYs7DeviceImgService;
import org.dromara.other.service.IOthYs7DeviceService; import org.dromara.other.service.IOthYs7DeviceService;
import org.dromara.out.domain.OutConstructionValue; import org.dromara.out.domain.OutConstructionValue;
import org.dromara.out.domain.OutConstructionValueRange; import org.dromara.out.domain.OutConstructionValueRange;
@ -55,6 +57,8 @@ import java.time.LocalDate;
import java.time.temporal.TemporalAdjusters; import java.time.temporal.TemporalAdjusters;
import java.util.*; import java.util.*;
import java.util.function.Function; import java.util.function.Function;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors; import java.util.stream.Collectors;
/** /**
@ -112,6 +116,9 @@ public class DemoTest {
@Resource @Resource
private IOthYs7DeviceService ys7DeviceService; private IOthYs7DeviceService ys7DeviceService;
@Resource
private IOthYs7DeviceImgService ys7DeviceImgService;
@Resource @Resource
private Ys7Manager ys7Manager; private Ys7Manager ys7Manager;
@ -547,4 +554,38 @@ public class DemoTest {
} }
} }
@Test
void capturePic() {
List<String> urlList = List.of(
"http://xny.yj-3d.com:9000/xinnengyuan-dev/2025/10/23/db8a379b456142459852b654f20d5f97.png",
"http://xny.yj-3d.com:9000/xinnengyuan-dev/2025/10/23/913dbcf0f7244c8b878e84b5525bec4b.png",
"http://xny.yj-3d.com:9000/xinnengyuan-dev/2025/10/23/2b904765f03f40b2ad0ddbf6ddeadb45.png"
);
for (String url : urlList) {
Pattern pattern = Pattern.compile(".*/device/img/([^/]+)/.*");
Matcher matcher = pattern.matcher(url);
OthYs7Device ys7Device = ys7DeviceService.lambdaQuery()
.eq(OthYs7Device::getDeviceSerial, "GA1730672")
.last("limit 1")
.one();
if (ys7Device == null) {
throw new ServiceException("设备不存在", HttpStatus.ERROR);
}
String deviceSerial = ys7Device.getDeviceSerial();
// 如果没有预置位,则直接对默认通道抓图
OthYs7DeviceImgCreateByCapture img = new OthYs7DeviceImgCreateByCapture();
img.setProjectId(ys7Device.getProjectId());
img.setDeviceSerial(deviceSerial);
img.setDeviceName(ys7Device.getDeviceName());
// String url = "http://xny.yj-3d.com:9000/xinnengyuan/ys7/device/img/GA1044315/2025-10-13_859fdfb7dde540608356f29cb9e3d63e.jpg";
// String url = "http://xny.yj-3d.com:9000/xinnengyuan/ys7/device/img/GA1044315/2025-10-12_2801707255b84004acb5fee2a75299b2.jpg";
img.setCreateTime(new Date());
img.setUrl(url);
log.info("图片:{},识别中", url);
ys7DeviceImgService.saveCapturePic(List.of(img));
}
}
} }

View File

@ -23,7 +23,7 @@ public class RecognizerTest {
@Test @Test
void test() { void test() {
RecognizeVo recognize = recognizerManager.recognize("http://xny.yj-3d.com:7363/file/tif/20250625160218orthophoto.png", List.of(RecognizerTypeEnum.SOLAR)); RecognizeVo recognize = recognizerManager.recognize("http://xny.yj-3d.com:7363/file/tif/20250625160218orthophoto.png", List.of(RecognizerTypeEnum.PANEL));
log.info("recognize: {}", recognize); log.info("recognize: {}", recognize);
} }
} }

View File

@ -1,9 +1,17 @@
package org.dromara.test; package org.dromara.test;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import jakarta.annotation.Resource; import jakarta.annotation.Resource;
import org.dromara.common.core.utils.MapstructUtils;
import org.dromara.safety.domain.dto.violationrecord.HseViolationRecordCreateDto; import org.dromara.safety.domain.dto.violationrecord.HseViolationRecordCreateDto;
import org.dromara.safety.service.IHseViolationRecordService; import org.dromara.safety.service.IHseViolationRecordService;
import org.dromara.system.domain.SysMenu;
import org.dromara.system.domain.vo.SysMenuVo;
import org.dromara.system.mapper.SysMenuMapper;
import org.dromara.system.service.ISysMenuService;
import org.hamcrest.core.Is;
import org.junit.jupiter.api.Test; import org.junit.jupiter.api.Test;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.test.context.SpringBootTest; import org.springframework.boot.test.context.SpringBootTest;
import java.util.ArrayList; import java.util.ArrayList;
@ -20,6 +28,9 @@ public class ViolationRecordTest {
@Resource @Resource
private IHseViolationRecordService violationRecordService; private IHseViolationRecordService violationRecordService;
@Autowired
private SysMenuMapper sysMenuMapper;
@Test @Test
void test() { void test() {
List<HseViolationRecordCreateDto> list = new ArrayList<>(); List<HseViolationRecordCreateDto> list = new ArrayList<>();
@ -55,4 +66,26 @@ public class ViolationRecordTest {
list.add(dto5); list.add(dto5);
violationRecordService.insertByMonitor(list); violationRecordService.insertByMonitor(list);
} }
@Test
void contextLoads() {
SysMenuVo sysMenuVo = sysMenusByList(1972500768346673154L);
System.out.println(sysMenuVo.toString());
}
SysMenuVo sysMenusByList(Long id) {
SysMenuVo sysMenus = new SysMenuVo();
List<SysMenu> res = sysMenuMapper.selectList(new LambdaQueryWrapper<SysMenu>().eq(SysMenu::getParentId, id));
if (res != null && res.size() > 0 ) {
sysMenus.setChildren(MapstructUtils.convert(res, SysMenuVo.class));
res.forEach(sysMenu -> {
sysMenusByList(sysMenu.getMenuId());
});
}
return sysMenus;
}
} }

View File

@ -0,0 +1,32 @@
package org.dromara.common.core.domain.vo;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
@Data
public class XzdCustomerSupplierVos implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
/**
*
*/
private Long id;
/**
* 类型1、供应商2、客户
*/
private String type;
/**
* 供应商-客户id
*/
private Long cSId;
}

View File

@ -0,0 +1,6 @@
package org.dromara.common.core.service;
public interface XzdCsContractInformationService {
String selectNameByIds(String ids);
}

View File

@ -0,0 +1,14 @@
package org.dromara.common.core.service;
import org.dromara.common.core.domain.vo.XzdCustomerSupplierVos;
public interface XzdCustomerSupplierService {
/**
* 查询供应商-客户中间
*
* @param id 主键
* @return 供应商-客户中间
*/
XzdCustomerSupplierVos queryByIdone(Long id);
}

View File

@ -0,0 +1,8 @@
package org.dromara.common.core.service;
public interface XzdCustomerinformationService {
String selectNmaeByIds(String id);
String selectNmaeById(Long id);
}

View File

@ -0,0 +1,6 @@
package org.dromara.common.core.service;
public interface XzdJsCgJungonService {
String selectNameByIds(String ids);
}

View File

@ -0,0 +1,6 @@
package org.dromara.common.core.service;
public interface XzdProjectService {
String selectNmaeByIds(String ids);
}

View File

@ -0,0 +1,5 @@
package org.dromara.common.core.service;
public interface XzdPurchaseContractInformationService {
String selectNameByIds(String ids);
}

View File

@ -0,0 +1,9 @@
package org.dromara.common.core.service;
public interface XzdSupplierInfoService {
String selectNmaeByIds(String ids);
String selectNmaeById(Long id);
}

View File

@ -0,0 +1,6 @@
package org.dromara.common.core.service;
public interface XzdSupplierOpenBankService {
String selectNameByIds(String ids);
}

View File

@ -37,4 +37,36 @@ public interface TransConstant {
*/ */
String PROJECT_ID_TO_NAME = "project_id_to_name"; String PROJECT_ID_TO_NAME = "project_id_to_name";
/**
* 客户id转名称
*/
String XZD_KHXX_ID_TO_NAME = "khxx_id_to_name";
// /**
// * 供应商id转名称
// */
// String XZD_KHXX_ID_TO_NAME = "gysxx_id_to_name";
/**
* 新中大项目id转名称
*/
String XZD_PROJECT_ID_TO_NAME = "xzd_project_id_to_name";
/**
* 采购合同id转名称
*/
String XZD_PURCHASE_CONTRACT_ID_TO_NAME = "xzd_purchase_contract_id_to_name";
/**
* 综合服务合同id转名称
*/
String XZD_CS_CONTRACT_INFORMATION_ID_TO_NAME = "xzd_cs_contract_information_id_to_name";
/**
* 结算-采购合同竣工结算id转名称
*/
String XZD_JS_CG_JUNGON_ID_TO_NAME = "xzd_js_cg_jungon_id_to_name";
/**
* 新中大供应商信息-开户银行id转银行名称
*/
String XZD_SUPPLIER_OPEN_BANK_ID_TO_NAME = "xzd_supplier_open_bank_id_to_name";
} }

View File

@ -0,0 +1,26 @@
package org.dromara.common.translation.core.impl;
import lombok.AllArgsConstructor;
import org.dromara.common.core.service.XzdCsContractInformationService;
import org.dromara.common.core.service.XzdPurchaseContractInformationService;
import org.dromara.common.translation.annotation.TranslationType;
import org.dromara.common.translation.constant.TransConstant;
import org.dromara.common.translation.core.TranslationInterface;
@AllArgsConstructor
@TranslationType(type = TransConstant.XZD_CS_CONTRACT_INFORMATION_ID_TO_NAME)
public class XzdCsContractInformationImpl implements TranslationInterface<String> {
private final XzdCsContractInformationService xzdCsContractInformationService;
@Override
public String translation(Object key, String other) {
if (key instanceof String ids) {
return xzdCsContractInformationService.selectNameByIds(ids);
} else if (key instanceof Long id) {
return xzdCsContractInformationService.selectNameByIds(id.toString());
}
return null;
}
}

View File

@ -0,0 +1,24 @@
package org.dromara.common.translation.core.impl;
import lombok.AllArgsConstructor;
import org.dromara.common.core.service.XzdCustomerinformationService;
import org.dromara.common.translation.annotation.TranslationType;
import org.dromara.common.translation.constant.TransConstant;
import org.dromara.common.translation.core.TranslationInterface;
@AllArgsConstructor
@TranslationType(type = TransConstant.XZD_KHXX_ID_TO_NAME)
public class XzdCustomerinformationImpl implements TranslationInterface<String> {
private final XzdCustomerinformationService xzdCustomerinformationService;
@Override
public String translation(Object key, String other) {
if (key instanceof String ids) {
return xzdCustomerinformationService.selectNmaeByIds(ids);
} else if (key instanceof Long id) {
return xzdCustomerinformationService.selectNmaeByIds(id.toString());
}
return null;
}
}

View File

@ -0,0 +1,23 @@
package org.dromara.common.translation.core.impl;
import lombok.AllArgsConstructor;
import org.dromara.common.core.service.XzdJsCgJungonService;
import org.dromara.common.translation.annotation.TranslationType;
import org.dromara.common.translation.constant.TransConstant;
import org.dromara.common.translation.core.TranslationInterface;
@AllArgsConstructor
@TranslationType(type = TransConstant.XZD_JS_CG_JUNGON_ID_TO_NAME)
public class XzdJsCgJungonImpl implements TranslationInterface<String> {
private final XzdJsCgJungonService xzdJsCgJungonService;
@Override
public String translation(Object key, String other) {
if (key instanceof String ids) {
return xzdJsCgJungonService.selectNameByIds(ids);
} else if (key instanceof Long id) {
return xzdJsCgJungonService.selectNameByIds(id.toString());
}
return null;
}
}

View File

@ -0,0 +1,23 @@
package org.dromara.common.translation.core.impl;
import lombok.AllArgsConstructor;
import org.dromara.common.core.service.XzdProjectService;
import org.dromara.common.translation.annotation.TranslationType;
import org.dromara.common.translation.constant.TransConstant;
import org.dromara.common.translation.core.TranslationInterface;
@AllArgsConstructor
@TranslationType(type = TransConstant.XZD_PROJECT_ID_TO_NAME)
public class XzdProjectImpl implements TranslationInterface<String> {
private final XzdProjectService xzdProjectService;
@Override
public String translation(Object key, String other) {
if (key instanceof String ids) {
return xzdProjectService.selectNmaeByIds(ids);
} else if (key instanceof Long id) {
return xzdProjectService.selectNmaeByIds(id.toString());
}
return null;
}
}

View File

@ -0,0 +1,26 @@
package org.dromara.common.translation.core.impl;
import lombok.AllArgsConstructor;
import org.dromara.common.core.service.XzdPurchaseContractInformationService;
import org.dromara.common.translation.annotation.TranslationType;
import org.dromara.common.translation.constant.TransConstant;
import org.dromara.common.translation.core.TranslationInterface;
@AllArgsConstructor
@TranslationType(type = TransConstant.XZD_PURCHASE_CONTRACT_ID_TO_NAME)
public class XzdPurchaseContractInformationImpl implements TranslationInterface<String> {
private final XzdPurchaseContractInformationService xzdCustomerinformationService;
@Override
public String translation(Object key, String other) {
if (key instanceof String ids) {
return xzdCustomerinformationService.selectNameByIds(ids);
} else if (key instanceof Long id) {
return xzdCustomerinformationService.selectNameByIds(id.toString());
}
return null;
}
}

View File

@ -0,0 +1,24 @@
package org.dromara.common.translation.core.impl;
import lombok.AllArgsConstructor;
import org.dromara.common.core.service.XzdSupplierInfoService;
import org.dromara.common.translation.annotation.TranslationType;
import org.dromara.common.translation.constant.TransConstant;
import org.dromara.common.translation.core.TranslationInterface;
@AllArgsConstructor
//@TranslationType(type = TransConstant.XZD_KHXX_ID_TO_NAME)
public class XzdSupplierInfoImpl implements TranslationInterface<String> {
private final XzdSupplierInfoService xzdSupplierInfoService;
@Override
public String translation(Object key, String other) {
if (key instanceof String ids) {
return xzdSupplierInfoService.selectNmaeByIds(ids);
} else if (key instanceof Long id) {
return xzdSupplierInfoService.selectNmaeByIds(id.toString());
}
return null;
}
}

View File

@ -0,0 +1,23 @@
package org.dromara.common.translation.core.impl;
import lombok.AllArgsConstructor;
import org.dromara.common.core.service.XzdSupplierOpenBankService;
import org.dromara.common.translation.annotation.TranslationType;
import org.dromara.common.translation.constant.TransConstant;
import org.dromara.common.translation.core.TranslationInterface;
@AllArgsConstructor
@TranslationType(type = TransConstant.XZD_SUPPLIER_OPEN_BANK_ID_TO_NAME)
public class XzdSupplierOpenBankImpl implements TranslationInterface<String> {
private final XzdSupplierOpenBankService xzdSupplierOpenBankService;
@Override
public String translation(Object key, String other) {
if (key instanceof String ids) {
return xzdSupplierOpenBankService.selectNameByIds(ids);
} else if (key instanceof Long id) {
return xzdSupplierOpenBankService.selectNameByIds(id.toString());
}
return null;
}
}

View File

@ -5,3 +5,10 @@ org.dromara.common.translation.core.impl.OssUrlTranslationImpl
org.dromara.common.translation.core.impl.UserNameTranslationImpl org.dromara.common.translation.core.impl.UserNameTranslationImpl
org.dromara.common.translation.core.impl.NicknameTranslationImpl org.dromara.common.translation.core.impl.NicknameTranslationImpl
org.dromara.common.translation.core.impl.ProjectNameTranslationImpl org.dromara.common.translation.core.impl.ProjectNameTranslationImpl
org.dromara.common.translation.core.impl.XzdCustomerinformationImpl
org.dromara.common.translation.core.impl.XzdProjectImpl
org.dromara.common.translation.core.impl.XzdPurchaseContractInformationImpl
org.dromara.common.translation.core.impl.XzdSupplierInfoImpl
org.dromara.common.translation.core.impl.XzdJsCgJungonImpl
org.dromara.common.translation.core.impl.XzdCsContractInformationImpl
org.dromara.common.translation.core.impl.XzdSupplierOpenBankImpl

View File

@ -15,16 +15,31 @@
system系统模块 system系统模块
</description> </description>
<dependencyManagement>
<dependencies>
<dependency>
<groupId>com.alibaba.cloud.ai</groupId>
<artifactId>spring-ai-alibaba-bom</artifactId>
<version>1.0.0.2</version>
<type>pom</type>
<scope>import</scope>
</dependency>
</dependencies>
</dependencyManagement>
<dependencies> <dependencies>
<dependency>
<groupId>com.alibaba.cloud.ai</groupId>
<artifactId>spring-ai-alibaba-starter-dashscope</artifactId>
</dependency>
<!-- Java WebSocket 标准API --> <!-- Java WebSocket 标准API -->
<!-- <dependency>--> <!-- <dependency>-->
<!-- <groupId>javax.websocket</groupId>--> <!-- <groupId>javax.websocket</groupId>-->
<!-- <artifactId>javax.websocket-api</artifactId>--> <!-- <artifactId>javax.websocket-api</artifactId>-->
<!-- <version>1.1</version>--> <!-- <version>1.1</version>-->
<!-- <scope>provided</scope>--> <!-- <scope>provided</scope>-->
<!-- </dependency>--> <!-- </dependency>-->
<dependency> <dependency>
<groupId>org.springframework.boot</groupId> <groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-websocket</artifactId> <artifactId>spring-boot-starter-websocket</artifactId>
@ -36,18 +51,18 @@
</exclusions> </exclusions>
</dependency> </dependency>
<!-- <dependency>--> <!-- <dependency>-->
<!-- <groupId>com.drewnoakes</groupId>--> <!-- <groupId>com.drewnoakes</groupId>-->
<!-- <artifactId>metadata-extractor</artifactId>--> <!-- <artifactId>metadata-extractor</artifactId>-->
<!-- <version>2.18.0</version>--> <!-- <version>2.18.0</version>-->
<!-- </dependency>--> <!-- </dependency>-->
<!-- <dependency>--> <!-- <dependency>-->
<!-- <groupId>technology.tabula</groupId>--> <!-- <groupId>technology.tabula</groupId>-->
<!-- <artifactId>tabula</artifactId>--> <!-- <artifactId>tabula</artifactId>-->
<!-- <version>1.0.4</version>--> <!-- <version>1.0.4</version>-->
<!-- </dependency>--> <!-- </dependency>-->
<!-- JSON解析FastJSON --> <!-- JSON解析FastJSON -->
@ -119,19 +134,18 @@
</dependency> </dependency>
<!-- 支持中文字体 --> <!-- 支持中文字体 -->
<!-- <dependency>--> <!-- <dependency>-->
<!-- <groupId>com.itextpdf</groupId>--> <!-- <groupId>com.itextpdf</groupId>-->
<!-- <artifactId>itext-asian</artifactId>--> <!-- <artifactId>itext-asian</artifactId>-->
<!-- <version>5.2.0</version>--> <!-- <version>5.2.0</version>-->
<!-- </dependency>--> <!-- </dependency>-->
<!-- &lt;!&ndash; iText &ndash;&gt;--> <!-- &lt;!&ndash; iText &ndash;&gt;-->
<!-- <dependency>--> <!-- <dependency>-->
<!-- <groupId>com.itextpdf</groupId>--> <!-- <groupId>com.itextpdf</groupId>-->
<!-- <artifactId>itextpdf</artifactId>--> <!-- <artifactId>itextpdf</artifactId>-->
<!-- <version>5.5.13.3</version>--> <!-- <version>5.5.13.3</version>-->
<!-- </dependency>--> <!-- </dependency>-->
<!-- ZXing --> <!-- ZXing -->
<dependency> <dependency>
<groupId>com.google.zxing</groupId> <groupId>com.google.zxing</groupId>

View File

@ -0,0 +1,51 @@
package org.dromara.ai.controller;
import com.alibaba.cloud.ai.dashscope.chat.DashScopeChatOptions;
import jakarta.servlet.http.HttpServletResponse;
import org.springframework.ai.chat.client.ChatClient;
import org.springframework.ai.chat.client.advisor.SimpleLoggerAdvisor;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import reactor.core.publisher.Flux;
/**
* @author lilemy
* @date 2025-10-23 11:32
*/
@Validated
@RestController
@RequestMapping("/ai")
public class AIController {
private static final String DEFAULT_PROMPT = "你是一个博学的智能聊天助手,请根据用户提问回答!";
private final ChatClient dashScopeChatClient;
public AIController(ChatClient.Builder chatClientBuilder) {
this.dashScopeChatClient = chatClientBuilder
.defaultSystem(DEFAULT_PROMPT)
// 实现 Logger 的 Advisor
.defaultAdvisors(
new SimpleLoggerAdvisor()
)
// 设置 ChatClient 中 ChatModel 的 Options 参数
.defaultOptions(
DashScopeChatOptions.builder()
.withTopP(0.7)
.build()
)
.build();
}
/**
* ChatClient 流式调用
*/
@GetMapping("/stream/chat")
public Flux<String> streamChat(@RequestParam(value = "query", defaultValue = "你好,很高兴认识你,能简单介绍一下自己吗?") String query, HttpServletResponse response) {
response.setCharacterEncoding("UTF-8");
return dashScopeChatClient.prompt(query).stream().content();
}
}

View File

@ -1,12 +1,21 @@
package org.dromara.common.utils; package org.dromara.common.utils;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j; import lombok.extern.slf4j.Slf4j;
import org.dromara.common.core.utils.MessageUtils; import org.dromara.common.core.utils.MessageUtils;
import org.dromara.common.sse.dto.SseMessageDto; import org.dromara.common.sse.dto.SseMessageDto;
import org.dromara.common.sse.utils.SseMessageUtils; import org.dromara.common.sse.utils.SseMessageUtils;
import org.dromara.contractor.domain.SubConstructionUser;
import org.dromara.mobileAttendanceMachine.DeviceMessageSender;
import org.dromara.mobileAttendanceMachine.KqjEntity;
import org.dromara.project.domain.BusAttendanceMachine;
import org.dromara.project.service.IBusAttendanceMachineService;
import org.dromara.sms4j.api.SmsBlend; import org.dromara.sms4j.api.SmsBlend;
import org.dromara.sms4j.api.entity.SmsResponse; import org.dromara.sms4j.api.entity.SmsResponse;
import org.dromara.sms4j.core.factory.SmsFactory; import org.dromara.sms4j.core.factory.SmsFactory;
import org.dromara.system.domain.vo.SysOssVo;
import org.dromara.system.service.ISysOssService;
import org.springframework.context.annotation.Lazy;
import org.springframework.scheduling.annotation.Async; import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Component; import org.springframework.stereotype.Component;
@ -17,6 +26,16 @@ import java.util.List;
@Slf4j @Slf4j
public class AsyncUtil { public class AsyncUtil {
@Resource
@Lazy
private DeviceMessageSender deviceMessageSender;
@Resource
@Lazy
private ISysOssService ossService;
@Resource
@Lazy
private IBusAttendanceMachineService attendanceMachineService;
//发送短信 //发送短信
@Async @Async
public void sendSms(List<String> mobileList, String config) { public void sendSms(List<String> mobileList, String config) {
@ -39,4 +58,27 @@ public class AsyncUtil {
} }
//下发考勤人员
@Async
public void sendPersonnel(Long teamId, SubConstructionUser constructionUser) {
SysOssVo byId = ossService.getById(Long.valueOf(constructionUser.getFacePic()));
List<BusAttendanceMachine> list = attendanceMachineService.lambdaQuery().apply("FIND_IN_SET({0}, teams)", teamId).list();
for (BusAttendanceMachine machine : list) {
deviceMessageSender.sendPersonnelInformation(machine.getSn(), constructionUser.getSysUserId().toString(), constructionUser.getUserName(), byId.getUrl());
}
}
//删除考勤人员
@Async
public void deletePersonnel(SubConstructionUser constructionUser) {
List<BusAttendanceMachine> list = attendanceMachineService.lambdaQuery().apply("FIND_IN_SET({0}, teams)", constructionUser.getTeamId()).list();
for (BusAttendanceMachine machine : list) {
try {
deviceMessageSender.deleteUser(machine.getSn(), constructionUser.getSysUserId().toString());
} catch (Exception e) {
log.error("删除考勤人员异常", e);
}
}
}
} }

View File

@ -364,10 +364,11 @@ public class SubConstructionUserController extends BaseController {
if (user.getEntryDate() != null) { if (user.getEntryDate() != null) {
vo.setEntryDate(DateUtils.formatDateTime(user.getEntryDate())); vo.setEntryDate(DateUtils.formatDateTime(user.getEntryDate()));
} }
//0男 1女 2未知
String sex = vo.getSex(); String sex = vo.getSex();
if (sex != null && sex.equals("1")) { if (sex != null && sex.equals("0")) {
vo.setSex(""); vo.setSex("");
} else if (sex != null && sex.equals("2")) { } else if (sex != null && sex.equals("1")) {
vo.setSex(""); vo.setSex("");
} else { } else {
vo.setSex("未知"); vo.setSex("未知");

View File

@ -101,4 +101,7 @@ public class SubConstructionUserQueryReq implements Serializable {
*/ */
private String userId; private String userId;
private String phone;
} }

View File

@ -26,6 +26,7 @@ import org.dromara.common.oss.core.OssClient;
import org.dromara.common.oss.exception.OssException; import org.dromara.common.oss.exception.OssException;
import org.dromara.common.oss.factory.OssFactory; import org.dromara.common.oss.factory.OssFactory;
import org.dromara.common.satoken.utils.LoginHelper; import org.dromara.common.satoken.utils.LoginHelper;
import org.dromara.common.utils.AsyncUtil;
import org.dromara.common.utils.IdCardEncryptorUtil; import org.dromara.common.utils.IdCardEncryptorUtil;
import org.dromara.common.utils.baiduUtil.BaiDuFace; import org.dromara.common.utils.baiduUtil.BaiDuFace;
import org.dromara.common.utils.baiduUtil.BaiDuOCR; import org.dromara.common.utils.baiduUtil.BaiDuOCR;
@ -46,6 +47,7 @@ import org.dromara.contractor.mapper.SubConstructionUserMapper;
import org.dromara.contractor.service.ISubConstructionUserFileService; import org.dromara.contractor.service.ISubConstructionUserFileService;
import org.dromara.contractor.service.ISubConstructionUserService; import org.dromara.contractor.service.ISubConstructionUserService;
import org.dromara.contractor.service.ISubContractorService; import org.dromara.contractor.service.ISubContractorService;
import org.dromara.mobileAttendanceMachine.DeviceMessageSender;
import org.dromara.project.domain.*; import org.dromara.project.domain.*;
import org.dromara.project.domain.enums.BusAttendanceClockStatusEnum; import org.dromara.project.domain.enums.BusAttendanceClockStatusEnum;
import org.dromara.project.domain.enums.BusAttendanceCommuterEnum; import org.dromara.project.domain.enums.BusAttendanceCommuterEnum;
@ -151,6 +153,11 @@ public class SubConstructionUserServiceImpl extends ServiceImpl<SubConstructionU
@Resource @Resource
private ISysRoleService roleService; private ISysRoleService roleService;
@Resource
private AsyncUtil asyncUtil;
/** /**
* 查询施工人员 * 查询施工人员
* *
@ -202,8 +209,10 @@ public class SubConstructionUserServiceImpl extends ServiceImpl<SubConstructionU
LambdaQueryWrapper<SubConstructionUser> lqw = Wrappers.lambdaQuery(); LambdaQueryWrapper<SubConstructionUser> lqw = Wrappers.lambdaQuery();
// 从对象中取值 // 从对象中取值
String userName = req.getUserName(); String userName = req.getUserName();
String phone = req.getPhone();
// 模糊查询 // 模糊查询
lqw.like(StringUtils.isNotBlank(phone), SubConstructionUser::getPhone, phone);
lqw.like(StringUtils.isNotBlank(userName), SubConstructionUser::getUserName, userName); lqw.like(StringUtils.isNotBlank(userName), SubConstructionUser::getUserName, userName);
lqw.isNull(SubConstructionUser::getProjectId); lqw.isNull(SubConstructionUser::getProjectId);
lqw.isNull(SubConstructionUser::getTeamId); lqw.isNull(SubConstructionUser::getTeamId);
@ -290,6 +299,8 @@ public class SubConstructionUserServiceImpl extends ServiceImpl<SubConstructionU
//强退 //强退
roleService.cleanOnlineUser(Collections.singletonList(constructionUser.getSysUserId())); roleService.cleanOnlineUser(Collections.singletonList(constructionUser.getSysUserId()));
asyncUtil.sendPersonnel(dto.getTeamId(), constructionUser);
return i > 0; return i > 0;
} }

View File

@ -1,17 +1,40 @@
package org.dromara.design.controller; package org.dromara.design.controller;
import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List; import java.util.List;
import java.util.Map;
import cn.hutool.core.util.StrUtil;
import com.deepoove.poi.XWPFTemplate;
import com.deepoove.poi.config.Configure;
import com.deepoove.poi.plugin.table.LoopRowTableRenderPolicy;
import jakarta.annotation.Resource; import jakarta.annotation.Resource;
import lombok.RequiredArgsConstructor; import lombok.RequiredArgsConstructor;
import jakarta.servlet.http.HttpServletResponse; import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.*; import jakarta.validation.constraints.*;
import cn.dev33.satoken.annotation.SaCheckPermission; import cn.dev33.satoken.annotation.SaCheckPermission;
import org.dromara.design.domain.BusDrawingreviewReceipts;
import org.dromara.design.domain.DesCollectFile;
import org.dromara.design.domain.DesDesignChange;
import org.dromara.design.domain.bo.DesUserBo; import org.dromara.design.domain.bo.DesUserBo;
import org.dromara.design.domain.dto.designchange.DesDesignExtendDetailDto;
import org.dromara.design.domain.vo.DesCollectFileWordVo;
import org.dromara.design.domain.vo.DesUserVo; import org.dromara.design.domain.vo.DesUserVo;
import org.dromara.design.domain.vo.designchange.DesDesignChangeVo;
import org.dromara.design.service.IDesDesignChangeService;
import org.dromara.design.service.IDesUserService; import org.dromara.design.service.IDesUserService;
import org.dromara.project.domain.BusProject;
import org.dromara.project.domain.vo.project.BusSubProjectVo; import org.dromara.project.domain.vo.project.BusSubProjectVo;
import org.dromara.project.service.IBusProjectService; import org.dromara.project.service.IBusProjectService;
import org.dromara.system.service.ISysDictDataService;
import org.dromara.system.service.ISysUserService;
import org.springframework.core.io.ClassPathResource;
import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import org.springframework.validation.annotation.Validated; import org.springframework.validation.annotation.Validated;
import org.dromara.common.idempotent.annotation.RepeatSubmit; import org.dromara.common.idempotent.annotation.RepeatSubmit;
@ -44,6 +67,12 @@ public class BusDrawingreviewReceiptsController extends BaseController {
private final IDesUserService desUserService; private final IDesUserService desUserService;
private final IDesDesignChangeService desDesignChangeService;
private final ISysDictDataService dictDataService;
private final ISysUserService userService;
/** /**
* 查询设计-图纸评审验证列表 * 查询设计-图纸评审验证列表
*/ */
@ -132,4 +161,85 @@ public class BusDrawingreviewReceiptsController extends BaseController {
return R.ok(desUserService.queryList(bo)); return R.ok(desUserService.queryList(bo));
} }
private static final String TEMPLATE_PATH = "template/设计验证表.docx";
@PostMapping("/downloadWord")
public void generateDesignLeaderDoc(Long id, HttpServletResponse response) {
OutputStream outputStream = null;
try {
// 1. 调用Service生成目标模板的Word字节流
byte[] docBytes = generateDocBytes(id);
// 2. 配置响应头:确保前端正确下载(避免中文乱码、指定文件类型)
response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE); // 二进制流类型
// 下载文件名:格式为“[项目名]-设计负责人任命通知单.docx”此处用projectId拼接真实场景可从数据中获取项目名
String downloadFileName = URLEncoder.encode(
"设计验证表.docx",
"UTF-8"
);
response.setHeader("Content-Disposition", "attachment;filename=" + downloadFileName);
response.setContentLength(docBytes.length); // 设置响应体长度(优化下载体验)
// 3. 将Word字节流写入响应
outputStream = response.getOutputStream();
outputStream.write(docBytes);
outputStream.flush();
} catch (Exception e) {
e.printStackTrace();
// 异常处理返回500错误状态码
response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
} finally {
// 关闭流,避免资源泄漏
if (outputStream != null) {
try {
outputStream.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
public byte[] generateDocBytes(Long id) throws Exception {
// -------------------------- 步骤1按projectId查询项目数据模拟真实业务 --------------------------
// 实际场景替换为数据库查询如调用DAO获取项目名称、负责人等
DesDesignChangeVo desDesignChangeVo = desDesignChangeService.queryById(id);
BusDrawingreviewReceipts receipts = busDrawingreviewReceiptsService.lambdaQuery()
.eq(BusDrawingreviewReceipts::getDrawingreviewId, id)
.last("limit 1")
.one();
DesDesignExtendDetailDto extendDetail = desDesignChangeVo.getExtendDetail();
String s = dictDataService.selectDictLabel("des_user_major", receipts.getProfessional());
String designerName = null;
if(StrUtil.isNotBlank(receipts.getDesigner())){
Long userId = Long.parseLong(receipts.getDesigner());
designerName= userService.queryNameById(userId);
}
Map<String, Object> placeholderData = new HashMap<>();
placeholderData.put("projectName", receipts.getProjectName());
placeholderData.put("subName",extendDetail.getSubName());
placeholderData.put("stage", receipts.getStage());
placeholderData.put("professionalName", s);
placeholderData.put("volume", receipts.getVolume());
placeholderData.put("designerName", designerName);
placeholderData.put("verificationOpinion", receipts.getVerificationOpinion());
placeholderData.put("executionOpinion", receipts.getExecutionOpinion());
// -------------------------- 步骤2用poi-tl加载目标模板并替换占位符 --------------------------
// 读取resources下的“设计项目负责人任命通知单.docx”模板
ClassPathResource templateResource = new ClassPathResource(TEMPLATE_PATH);
try (InputStream templateIs = templateResource.getInputStream();
ByteArrayOutputStream outputStream = new ByteArrayOutputStream()) {
XWPFTemplate template = XWPFTemplate.compile(templateIs).render(placeholderData);
// -------------------------- 步骤3将生成的文档写入字节流 --------------------------
template.write(outputStream);
template.close(); // 关闭模板资源
return outputStream.toByteArray();
}
}
} }

View File

@ -1,15 +1,31 @@
package org.dromara.design.controller; package org.dromara.design.controller;
import java.util.List; import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.URLEncoder;
import java.util.*;
import java.util.stream.Collectors;
import com.deepoove.poi.XWPFTemplate;
import com.deepoove.poi.config.Configure;
import com.deepoove.poi.plugin.table.LoopRowTableRenderPolicy;
import lombok.RequiredArgsConstructor; import lombok.RequiredArgsConstructor;
import jakarta.servlet.http.HttpServletResponse; import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.*; import jakarta.validation.constraints.*;
import cn.dev33.satoken.annotation.SaCheckPermission; import cn.dev33.satoken.annotation.SaCheckPermission;
import org.dromara.design.domain.DesCollectFile;
import org.dromara.design.domain.bo.DesCollectFileBo; import org.dromara.design.domain.bo.DesCollectFileBo;
import org.dromara.design.domain.dto.ExportDto; import org.dromara.design.domain.dto.ExportDto;
import org.dromara.design.domain.dto.designchange.DesDesignExtendDetailDto;
import org.dromara.design.domain.vo.DesCollectFileVo; import org.dromara.design.domain.vo.DesCollectFileVo;
import org.dromara.design.domain.vo.DesCollectFileWordVo;
import org.dromara.design.domain.vo.designchange.DesDesignChangeVo;
import org.dromara.design.service.IDesCollectFileService; import org.dromara.design.service.IDesCollectFileService;
import org.dromara.project.domain.BusProject;
import org.dromara.project.service.IBusProjectService;
import org.springframework.core.io.ClassPathResource;
import org.springframework.http.MediaType;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import org.springframework.validation.annotation.Validated; import org.springframework.validation.annotation.Validated;
import org.dromara.common.idempotent.annotation.RepeatSubmit; import org.dromara.common.idempotent.annotation.RepeatSubmit;
@ -39,6 +55,8 @@ public class DesCollectFileController extends BaseController {
private final IDesCollectFileService desCollectFileService; private final IDesCollectFileService desCollectFileService;
private final IBusProjectService projectService;
/** /**
* 查询收资文件列表 * 查询收资文件列表
*/ */
@ -106,7 +124,6 @@ public class DesCollectFileController extends BaseController {
return toAjax(desCollectFileService.deleteWithValidByIds(List.of(ids), true)); return toAjax(desCollectFileService.deleteWithValidByIds(List.of(ids), true));
} }
/** /**
* 上传资料文件 * 上传资料文件
*/ */
@ -119,10 +136,92 @@ public class DesCollectFileController extends BaseController {
return toAjax(desCollectFileService.addFile(file, catalogueId, projectId)); return toAjax(desCollectFileService.addFile(file, catalogueId, projectId));
} }
@PostMapping("/exportZip") @PostMapping("/exportZip")
public void exportZip(ExportDto dto, HttpServletResponse response) throws Exception { public void exportZip(ExportDto dto, HttpServletResponse response) throws Exception {
desCollectFileService.exportAsZip(dto, response); desCollectFileService.exportAsZip(dto, response);
} }
private static final String TEMPLATE_PATH = "template/设计输入资料清单及评审表.docx";
@PostMapping("/downloadWord")
public void generateDesignLeaderDoc(Long projectId, HttpServletResponse response) {
OutputStream outputStream = null;
try {
// 1. 调用Service生成目标模板的Word字节流
byte[] docBytes = generateDocBytes(projectId);
// 2. 配置响应头:确保前端正确下载(避免中文乱码、指定文件类型)
response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE); // 二进制流类型
// 下载文件名:格式为“[项目名]-设计负责人任命通知单.docx”此处用projectId拼接真实场景可从数据中获取项目名
String downloadFileName = URLEncoder.encode(
"设计输入资料清单及评审表.docx",
"UTF-8"
);
response.setHeader("Content-Disposition", "attachment;filename=" + downloadFileName);
response.setContentLength(docBytes.length); // 设置响应体长度(优化下载体验)
// 3. 将Word字节流写入响应
outputStream = response.getOutputStream();
outputStream.write(docBytes);
outputStream.flush();
} catch (Exception e) {
e.printStackTrace();
// 异常处理返回500错误状态码
response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
} finally {
// 关闭流,避免资源泄漏
if (outputStream != null) {
try {
outputStream.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
public byte[] generateDocBytes(Long projectId) throws Exception {
// -------------------------- 步骤1按projectId查询项目数据模拟真实业务 --------------------------
// 实际场景替换为数据库查询如调用DAO获取项目名称、负责人等
List<DesCollectFile> list = desCollectFileService.lambdaQuery()
.eq(DesCollectFile::getProjectId, projectId).list();
List<DesCollectFileWordVo> files = new ArrayList<>();
int i = 1;
for (DesCollectFile desCollectFile : list) {
DesCollectFileWordVo desCollectFileWordVo = new DesCollectFileWordVo();
desCollectFileWordVo.setNum(i);
i++;
desCollectFileWordVo.setFileName(desCollectFile.getFileName());
files.add(desCollectFileWordVo);
}
BusProject project = projectService.getById(projectId);
Map<String, Object> placeholderData = new HashMap<>();
placeholderData.put("projectName", project.getProjectName());
placeholderData.put("files",files);
// -------------------------- 步骤2用poi-tl加载目标模板并替换占位符 --------------------------
// 读取resources下的“设计项目负责人任命通知单.docx”模板
ClassPathResource templateResource = new ClassPathResource(TEMPLATE_PATH);
try (InputStream templateIs = templateResource.getInputStream();
ByteArrayOutputStream outputStream = new ByteArrayOutputStream()) {
LoopRowTableRenderPolicy policy = new LoopRowTableRenderPolicy();
Configure config = Configure.builder()
.bind("files", policy).build();
XWPFTemplate template = XWPFTemplate.compile(templateIs, config).render(placeholderData);
// -------------------------- 步骤3将生成的文档写入字节流 --------------------------
template.write(outputStream);
template.close(); // 关闭模板资源
return outputStream.toByteArray();
}
}
} }

View File

@ -2,10 +2,13 @@ package org.dromara.design.controller;
import cn.dev33.satoken.annotation.SaCheckPermission; import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.hutool.core.collection.CollUtil; import cn.hutool.core.collection.CollUtil;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import jakarta.annotation.Resource; import jakarta.annotation.Resource;
import jakarta.servlet.http.HttpServletResponse; import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.NotEmpty; import jakarta.validation.constraints.NotEmpty;
import jakarta.validation.constraints.NotNull; import jakarta.validation.constraints.NotNull;
import org.apache.poi.xwpf.usermodel.*;
import org.dromara.common.core.domain.R; import org.dromara.common.core.domain.R;
import org.dromara.common.excel.utils.ExcelUtil; import org.dromara.common.excel.utils.ExcelUtil;
import org.dromara.common.idempotent.annotation.RepeatSubmit; import org.dromara.common.idempotent.annotation.RepeatSubmit;
@ -13,18 +16,37 @@ import org.dromara.common.log.annotation.Log;
import org.dromara.common.log.enums.BusinessType; import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.web.core.BaseController; import org.dromara.common.web.core.BaseController;
import org.dromara.design.domain.DesConstructionSchedulePlan; import org.dromara.design.domain.DesConstructionSchedulePlan;
import org.dromara.design.domain.DesUser;
import org.dromara.design.domain.dto.constructionscheduleplan.*; import org.dromara.design.domain.dto.constructionscheduleplan.*;
import org.dromara.design.domain.vo.DesConstructionSchedulePlanVo; import org.dromara.design.domain.vo.DesConstructionSchedulePlanVo;
import org.dromara.design.exportUtil.plan.AttachmentPersonnel;
import org.dromara.design.service.IDesConstructionSchedulePlanService; import org.dromara.design.service.IDesConstructionSchedulePlanService;
import org.dromara.design.service.IDesUserService;
import org.dromara.system.domain.vo.SysDictDataVo;
import org.dromara.system.service.ISysDictDataService;
import org.dromara.system.service.ISysDictTypeService;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTPPr;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTRow;
import org.openxmlformats.schemas.wordprocessingml.x2006.main.CTTcPr;
import org.springframework.core.io.ClassPathResource;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.validation.annotation.Validated; import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile; import org.springframework.web.multipart.MultipartFile;
import java.io.IOException; import java.io.*;
import java.util.List; import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.util.*;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import java.util.stream.Collectors;
import org.apache.poi.poifs.filesystem.POIFSFileSystem;
/** /**
* 设计计划 * 设计计划
* *
@ -38,7 +60,10 @@ public class DesConstructionSchedulePlanController extends BaseController {
@Resource @Resource
private IDesConstructionSchedulePlanService desConstructionSchedulePlanService; private IDesConstructionSchedulePlanService desConstructionSchedulePlanService;
@Resource
private IDesUserService desUserService;
@Resource
private ISysDictTypeService dictTypeService;
/** /**
* 查询设计计划列表 * 查询设计计划列表
*/ */
@ -150,4 +175,168 @@ public class DesConstructionSchedulePlanController extends BaseController {
desConstructionSchedulePlanService.exportSchedule(response,projectId); desConstructionSchedulePlanService.exportSchedule(response,projectId);
} }
private static final String TEMPLATE_RESOURCE_PATH = "template/CCCET-JL-CX-25设计计划表.docx";
// -------------------------- 2. 核心接口:修复单元格清空逻辑与数据填充 --------------------------
@PostMapping("/downloadWord")
public void fillCccetTemplate(Long projectId, HttpServletResponse response) {
// 1. 基础参数校验(避免空数据)
// 2. 读取resource中的模板+填充数据
try (
// 关键通过ClassPathResource读取resource/template下的模板
InputStream templateIs = new ClassPathResource(TEMPLATE_RESOURCE_PATH).getInputStream();
XWPFDocument doc = new XWPFDocument(templateIs); // 加载模板
OutputStream out = response.getOutputStream() // 响应流
) {
// --------------------------
// 步骤1填充第1页-主信息表索引0固定6列
// --------------------------
// XWPFTable mainTable = doc.getTables().get(0);
// // 工程名称第1行第0列
// if (mainTable.getRows().size() > 1 && mainTable.getRow(1).getCell(0) != null) {
// mainTable.getRow(1).getCell(0).setText(request.getProjectName() == null ? "" : request.getProjectName());
// }
// // 工程号第1行第1列
// if (mainTable.getRows().size() > 1 && mainTable.getRow(1).getCell(1) != null) {
// mainTable.getRow(1).getCell(1).setText(request.getProjectNo());
// }
// // 编制日期第2行第3列
// if (mainTable.getRows().size() > 2 && mainTable.getRow(2).getCell(3) != null) {
// mainTable.getRow(2).getCell(3).setText(request.getCompileDate() == null ? "" : request.getCompileDate());
// }
// // 编制人第3行第0列
// if (mainTable.getRows().size() > 3 && mainTable.getRow(3).getCell(0) != null) {
// mainTable.getRow(3).getCell(0).setText(request.getCompiler() == null ? "" : request.getCompiler());
// }
// // 批准人第3行第2列
// if (mainTable.getRows().size() > 3 && mainTable.getRow(3).getCell(2) != null) {
// mainTable.getRow(3).getCell(2).setText(request.getApprover() == null ? "" : request.getApprover());
// }
// // 设计阶段第3行第4列
// if (mainTable.getRows().size() > 3 && mainTable.getRow(3).getCell(4) != null) {
// mainTable.getRow(3).getCell(4).setText(request.getDesignStage() == null ? "" : request.getDesignStage());
// }
// // 设计规模第4行第0列
// if (mainTable.getRows().size() > 4 && mainTable.getRow(4).getCell(0) != null) {
// mainTable.getRow(4).getCell(0).setText(request.getDesignScale() == null ? "" : request.getDesignScale());
// }
// --------------------------
// 步骤2填充第3页-附件1人员配置表索引2固定11列
// --------------------------
XWPFTable staffTable = doc.getTables().get(2);
// 删除模板中附件1的空数据行保留第0行表头
while (staffTable.getRows().size() > 2) {
staffTable.removeRow(1);
}
List<AttachmentPersonnel> list = getPersonnelDataByProjectId(projectId);
for (AttachmentPersonnel staff : list) {
XWPFTableRow newRow = staffTable.createRow();
// 补全11列避免POI默认列数不足导致null
while (newRow.getTableCells().size() < 11) {
newRow.createCell();
}
// 按附件1列顺序填充
newRow.getCell(0).setText(staff.getProfessional() == null ? "" : staff.getProfessional());
newRow.getCell(1).setText(staff.getLeaderName() == null ? "" : staff.getLeaderName());
newRow.getCell(2).setText(staff.getLeaderTitle() == null ? "" : staff.getLeaderTitle());
newRow.getCell(3).setText(staff.getDesignerName() == null ? "" : staff.getDesignerName());
newRow.getCell(4).setText(staff.getDesignerTitle() == null ? "" : staff.getDesignerTitle());
newRow.getCell(5).setText(staff.getReviewerName() == null ? "" : staff.getReviewerName());
newRow.getCell(6).setText(staff.getReviewerTitle() == null ? "" : staff.getReviewerTitle());
newRow.getCell(7).setText(staff.getCheckerName() == null ? "" : staff.getCheckerName());
newRow.getCell(8).setText(staff.getCheckerTitle() == null ? "" : staff.getCheckerTitle());
newRow.getCell(9).setText(staff.getApproverName() == null ? "" : staff.getApproverName());
newRow.getCell(10).setText(staff.getApproverTitle() == null ? "" : staff.getApproverTitle());
}
// --------------------------
// 步骤3设置响应头触发前端下载
// --------------------------
response.setContentType("application/octet-stream");
// 文件名填充后_工程号_CCCET-JL-CX-25设计计划表.docx
String fileName = "CCCET-JL-CX-25设计计划表.docx";
response.setHeader("Content-Disposition",
"attachment;filename=" + URLEncoder.encode(fileName, StandardCharsets.UTF_8));
response.setHeader("Access-Control-Expose-Headers", "Content-Disposition"); // 允许前端获取文件名
// --------------------------
// 步骤4写出文件到前端
// --------------------------
doc.write(out);
out.flush();
} catch (Exception e) {
// 异常封装(前端可捕获具体错误)
throw new RuntimeException("CCCET-JL-CX-25模板填充失败" + e.getMessage());
}
}
/**
* 根据projectId获取数据仅针对CCCET-JL-CX-25设计计划表.docx附件1
*/
private List<AttachmentPersonnel> getPersonnelDataByProjectId(Long projectId) {
// 模拟数据库查询实际项目替换为真实Service调用
List<DesUser> userList = desUserService.list(Wrappers.<DesUser>lambdaQuery()
.eq(DesUser::getProjectId, projectId)
);
if (userList.isEmpty()) {
return Collections.emptyList();
}
// 专业字典映射(编码→名称)
List<SysDictDataVo> majorDict = dictTypeService.selectDictDataByType("des_user_major");
Map<String, String> majorMap = majorDict.stream()
.collect(Collectors.toMap(SysDictDataVo::getDictValue, SysDictDataVo::getDictLabel));
// 按角色分组1-专业负责人2-设计人3-校审人4-审定人5-审核人)
DesUser leader = userList.stream().filter(u -> "1".equals(u.getUserType())).findFirst().orElse(null);
Map<String, List<DesUser>> designerMap = userList.stream()
.filter(u -> "2".equals(u.getUserType()))
.collect(Collectors.groupingBy(DesUser::getUserMajor));
Map<String, List<DesUser>> reviewerMap = userList.stream()
.filter(u -> "3".equals(u.getUserType()))
.collect(Collectors.groupingBy(DesUser::getUserMajor));
Map<String, List<DesUser>> checkerMap = userList.stream()
.filter(u -> "5".equals(u.getUserType()))
.collect(Collectors.groupingBy(DesUser::getUserMajor));
Map<String, List<DesUser>> approverMap = userList.stream()
.filter(u -> "4".equals(u.getUserType()))
.collect(Collectors.groupingBy(DesUser::getUserMajor));
// 构建附件1数据一个专业一行避免重复
List<AttachmentPersonnel> dataList = new ArrayList<>();
for (Map.Entry<String, List<DesUser>> entry : designerMap.entrySet()) {
String majorCode = entry.getKey();
String majorName = majorMap.getOrDefault(majorCode, majorCode);
List<DesUser> designers = entry.getValue();
// 获取对应专业的其他角色
DesUser reviewer = reviewerMap.getOrDefault(majorCode, Collections.emptyList()).stream().findFirst().orElse(null);
DesUser checker = checkerMap.getOrDefault(majorCode, Collections.emptyList()).stream().findFirst().orElse(null);
DesUser approver = approverMap.getOrDefault(majorCode, Collections.emptyList()).stream().findFirst().orElse(null);
// 封装数据(多个设计人用顿号分隔)
AttachmentPersonnel data = new AttachmentPersonnel();
data.setProfessional(majorName);
data.setLeaderName(leader != null ? leader.getUserName() : "");
//data.setLeadeTitle(leader != null ? leader.getUserTitle() : "");
data.setDesignerName(designers.stream().map(DesUser::getUserName).collect(Collectors.joining("")));
//data.setDesignerTitle(designers.stream().map(DesUser::getUserTitle).collect(Collectors.joining("、")));
data.setReviewerName(reviewer != null ? reviewer.getUserName() : "");
//data.setReviewerTitle(reviewer != null ? reviewer.getUserTitle() : "");
data.setCheckerName(checker != null ? checker.getUserName() : "");
//data.setCheckerTitle(checker != null ? checker.getUserTitle() : "");
data.setApproverName(approver != null ? approver.getUserName() : "");
//data.setApproverTitle(approver != null ? approver.getUserTitle() : "");
dataList.add(data);
}
return dataList;
}
} }

View File

@ -2,6 +2,7 @@ package org.dromara.design.controller;
import cn.dev33.satoken.annotation.SaCheckPermission; import cn.dev33.satoken.annotation.SaCheckPermission;
import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.deepoove.poi.XWPFTemplate;
import jakarta.annotation.Resource; import jakarta.annotation.Resource;
import jakarta.servlet.http.HttpServletResponse; import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.NotEmpty; import jakarta.validation.constraints.NotEmpty;
@ -16,24 +17,36 @@ import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.mybatis.core.page.PageQuery; import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo; import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.web.core.BaseController; import org.dromara.common.web.core.BaseController;
import org.dromara.design.domain.DesUser;
import org.dromara.design.domain.DesVolumeCatalog; import org.dromara.design.domain.DesVolumeCatalog;
import org.dromara.design.domain.DesVolumeFile; import org.dromara.design.domain.DesVolumeFile;
import org.dromara.design.domain.dto.designchange.DesDesignChangeCreateReq; import org.dromara.design.domain.dto.designchange.DesDesignChangeCreateReq;
import org.dromara.design.domain.dto.designchange.DesDesignChangeQueryReq; import org.dromara.design.domain.dto.designchange.DesDesignChangeQueryReq;
import org.dromara.design.domain.dto.designchange.DesDesignChangeUpdateReq; import org.dromara.design.domain.dto.designchange.DesDesignChangeUpdateReq;
import org.dromara.design.domain.dto.designchange.DesDesignExtendDetailDto;
import org.dromara.design.domain.dto.volumecatalog.DesVolumeCatalogQueryReq; import org.dromara.design.domain.dto.volumecatalog.DesVolumeCatalogQueryReq;
import org.dromara.design.domain.vo.designchange.DesDesignChangeVo; import org.dromara.design.domain.vo.designchange.DesDesignChangeVo;
import org.dromara.design.domain.vo.volumecatalog.DesVolumeCatalogVo; import org.dromara.design.domain.vo.volumecatalog.DesVolumeCatalogVo;
import org.dromara.design.service.IDesDesignChangeService; import org.dromara.design.service.IDesDesignChangeService;
import org.dromara.design.service.IDesVolumeCatalogService; import org.dromara.design.service.IDesVolumeCatalogService;
import org.dromara.design.service.IDesVolumeFileService; import org.dromara.design.service.IDesVolumeFileService;
import org.dromara.project.domain.BusProject;
import org.dromara.system.domain.vo.SysOssVo; import org.dromara.system.domain.vo.SysOssVo;
import org.dromara.system.service.ISysDictDataService;
import org.dromara.system.service.ISysOssService; import org.dromara.system.service.ISysOssService;
import org.springframework.core.io.ClassPathResource;
import org.springframework.http.MediaType;
import org.springframework.validation.annotation.Validated; import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import java.io.ByteArrayOutputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.URLEncoder;
import java.util.Arrays; import java.util.Arrays;
import java.util.HashMap;
import java.util.List; import java.util.List;
import java.util.Map;
import java.util.stream.Collectors; import java.util.stream.Collectors;
/** /**
@ -56,6 +69,9 @@ public class DesDesignChangeController extends BaseController {
@Resource @Resource
private IDesVolumeFileService desVolumeFileService; private IDesVolumeFileService desVolumeFileService;
@Resource
private ISysDictDataService dictDataService;
/** /**
* 查询设计变更管理列表 * 查询设计变更管理列表
*/ */
@ -146,4 +162,92 @@ public class DesDesignChangeController extends BaseController {
return R.ok(list); return R.ok(list);
} }
private static final String TEMPLATE_PATH = "template/设计更改通知单.docx";
@PostMapping("/downloadWord")
public void generateDesignLeaderDoc(Long id, HttpServletResponse response) {
OutputStream outputStream = null;
try {
// 1. 调用Service生成目标模板的Word字节流
byte[] docBytes = generateDocBytes(id);
// 2. 配置响应头:确保前端正确下载(避免中文乱码、指定文件类型)
response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE); // 二进制流类型
// 下载文件名:格式为“[项目名]-设计负责人任命通知单.docx”此处用projectId拼接真实场景可从数据中获取项目名
String downloadFileName = URLEncoder.encode(
"设计更改通知单.docx",
"UTF-8"
);
response.setHeader("Content-Disposition", "attachment;filename=" + downloadFileName);
response.setContentLength(docBytes.length); // 设置响应体长度(优化下载体验)
// 3. 将Word字节流写入响应
outputStream = response.getOutputStream();
outputStream.write(docBytes);
outputStream.flush();
} catch (Exception e) {
e.printStackTrace();
// 异常处理返回500错误状态码
response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
} finally {
// 关闭流,避免资源泄漏
if (outputStream != null) {
try {
outputStream.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
public byte[] generateDocBytes(Long id) throws Exception {
// -------------------------- 步骤1按projectId查询项目数据模拟真实业务 --------------------------
// 实际场景替换为数据库查询如调用DAO获取项目名称、负责人等
DesDesignChangeVo vo = desDesignChangeService.queryById(id);
DesDesignExtendDetailDto extendDetail = vo.getExtendDetail()==null?new DesDesignExtendDetailDto():vo.getExtendDetail();
Map<String, Object> placeholderData = new HashMap<>();
placeholderData.put("projectName", vo.getProjectName());
placeholderData.put("designPhase",extendDetail.getDesignPhase());
placeholderData.put("subName",extendDetail.getSubName());
String s = dictDataService.selectDictLabel("des_user_major", vo.getSpecialty());
placeholderData.put("specialty",s);
placeholderData.put("volumeNo",vo.getVolumeNo());
String changeReason = vo.getChangeReason();
List<String> reasons = Arrays.asList("设计漏项", "设计改进", "设计差错", "接口差错",
"业主要求", "施工承包商要求", "外部资料与最终情况不符", "材料代用或其他");
String reason = reasons.stream()
.map(item -> changeReason.contains(String.valueOf(reasons.indexOf(item) + 1)) ? "" + item : "" + item)
.collect(Collectors.joining());
placeholderData.put("changeReason", reason);
placeholderData.put("designDisposal1", "1".equals(extendDetail.getDesignDisposal())?"" : "");
placeholderData.put("designDisposal2", "2".equals(extendDetail.getDesignDisposal())?"" : "");
placeholderData.put("designDisposal3", "3".equals(extendDetail.getDesignDisposal())?"" : "");
placeholderData.put("changeContent",vo.getChangeContent());
placeholderData.put("changeCategory1", "1".equals(extendDetail.getChangeCategory())?"" : "");
placeholderData.put("changeCategory2", "2".equals(extendDetail.getChangeCategory())?"" : "");
placeholderData.put("involvingProfessions", extendDetail.getInvolvingProfessions());
// -------------------------- 步骤2用poi-tl加载目标模板并替换占位符 --------------------------
// 读取resources下的“设计项目负责人任命通知单.docx”模板
ClassPathResource templateResource = new ClassPathResource(TEMPLATE_PATH);
try (InputStream templateIs = templateResource.getInputStream();
ByteArrayOutputStream outputStream = new ByteArrayOutputStream()) {
// 1. 加载模板 2. 注入替换数据 3. 渲染生成新文档
XWPFTemplate template = XWPFTemplate.compile(templateIs)
.render(placeholderData); // 自动匹配{{变量名}}占位符
// -------------------------- 步骤3将生成的文档写入字节流 --------------------------
template.write(outputStream);
template.close(); // 关闭模板资源
return outputStream.toByteArray();
}
}
} }

View File

@ -129,6 +129,7 @@ public class DesExtractController extends BaseController {
@SaCheckPermission("design:extract:userMajor") @SaCheckPermission("design:extract:userMajor")
@GetMapping("/userMajor") @GetMapping("/userMajor")
public R<List<DesUserVo>> selectUserMajor(DesUserBo bo) { public R<List<DesUserVo>> selectUserMajor(DesUserBo bo) {
bo.setUserType("1");
return R.ok( deUserService.queryList(bo)); return R.ok( deUserService.queryList(bo));
} }

View File

@ -1,16 +1,18 @@
package org.dromara.design.controller; package org.dromara.design.controller;
import java.io.ByteArrayOutputStream;
import java.io.IOException; import java.io.IOException;
import java.io.InputStream; import java.io.InputStream;
import java.io.OutputStream;
import java.net.URLEncoder;
import java.rmi.ServerException; import java.rmi.ServerException;
import java.time.LocalDate; import java.time.LocalDate;
import java.time.ZoneId; import java.time.ZoneId;
import java.util.ArrayList; import java.util.*;
import java.util.Collections;
import java.util.Date;
import java.util.List;
import com.baomidou.mybatisplus.core.toolkit.CollectionUtils; import com.baomidou.mybatisplus.core.toolkit.CollectionUtils;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.deepoove.poi.XWPFTemplate;
import lombok.RequiredArgsConstructor; import lombok.RequiredArgsConstructor;
import jakarta.servlet.http.HttpServletResponse; import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.*; import jakarta.validation.constraints.*;
@ -22,8 +24,15 @@ import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.xssf.usermodel.XSSFSheet; import org.apache.poi.xssf.usermodel.XSSFSheet;
import org.apache.poi.xssf.usermodel.XSSFWorkbook; import org.apache.poi.xssf.usermodel.XSSFWorkbook;
//import org.dromara.design.domain.DesUserExcelData; //import org.dromara.design.domain.DesUserExcelData;
import org.dromara.design.domain.DesUser;
import org.dromara.design.domain.DesUserExcelData; import org.dromara.design.domain.DesUserExcelData;
import org.dromara.design.domain.dto.desUser.DesUserBatchDto; import org.dromara.design.domain.dto.desUser.DesUserBatchDto;
import org.dromara.project.domain.BusProject;
import org.dromara.project.service.IBusProjectService;
import org.springframework.core.io.ClassPathResource;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
import org.springframework.validation.annotation.Validated; import org.springframework.validation.annotation.Validated;
import org.dromara.common.idempotent.annotation.RepeatSubmit; import org.dromara.common.idempotent.annotation.RepeatSubmit;
@ -54,6 +63,7 @@ import org.springframework.web.multipart.MultipartFile;
public class DesUserController extends BaseController { public class DesUserController extends BaseController {
private final IDesUserService desUserService; private final IDesUserService desUserService;
private final IBusProjectService projectService;
/** /**
* 查询设计人员列表 * 查询设计人员列表
@ -142,5 +152,75 @@ public class DesUserController extends BaseController {
return toAjax(desUserService.batchAddOrUpdate(dto)); return toAjax(desUserService.batchAddOrUpdate(dto));
} }
private static final String TEMPLATE_PATH = "template/设计项目负责人任命通知单.docx";
@PostMapping("/downloadWord")
public void generateDesignLeaderDoc( Long projectId,
HttpServletResponse response
) {
OutputStream outputStream = null;
try {
// 1. 调用Service生成目标模板的Word字节流
byte[] docBytes = generateDocBytes(projectId);
// 2. 配置响应头:确保前端正确下载(避免中文乱码、指定文件类型)
response.setContentType(MediaType.APPLICATION_OCTET_STREAM_VALUE); // 二进制流类型
// 下载文件名:格式为“[项目名]-设计负责人任命通知单.docx”此处用projectId拼接真实场景可从数据中获取项目名
String downloadFileName = URLEncoder.encode(
"设计负责人任命通知单.docx",
"UTF-8"
);
response.setHeader("Content-Disposition", "attachment;filename=" + downloadFileName);
response.setContentLength(docBytes.length); // 设置响应体长度(优化下载体验)
// 3. 将Word字节流写入响应
outputStream = response.getOutputStream();
outputStream.write(docBytes);
outputStream.flush();
} catch (Exception e) {
e.printStackTrace();
// 异常处理返回500错误状态码
response.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
} finally {
// 关闭流,避免资源泄漏
if (outputStream != null) {
try {
outputStream.close();
} catch (Exception e) {
e.printStackTrace();
}
}
}
}
public byte[] generateDocBytes(Long projectId) throws Exception {
// -------------------------- 步骤1按projectId查询项目数据模拟真实业务 --------------------------
// 实际场景替换为数据库查询如调用DAO获取项目名称、负责人等
BusProject byId = projectService.getById(projectId);
DesUser desUser = desUserService.lambdaQuery().eq(DesUser::getProjectId, projectId)
.eq(DesUser::getUserType, "1")
.last("limit 1").one();
Map<String, Object> placeholderData = new HashMap<>();
placeholderData.put("projectName", byId==null?"" :byId.getProjectName());
placeholderData.put("leaderName",desUser==null?"": desUser.getUserName());
// -------------------------- 步骤2用poi-tl加载目标模板并替换占位符 --------------------------
// 读取resources下的“设计项目负责人任命通知单.docx”模板
ClassPathResource templateResource = new ClassPathResource(TEMPLATE_PATH);
try (InputStream templateIs = templateResource.getInputStream();
ByteArrayOutputStream outputStream = new ByteArrayOutputStream()) {
// 1. 加载模板 2. 注入替换数据 3. 渲染生成新文档
XWPFTemplate template = XWPFTemplate.compile(templateIs)
.render(placeholderData); // 自动匹配{{变量名}}占位符
// -------------------------- 步骤3将生成的文档写入字节流 --------------------------
template.write(outputStream);
template.close(); // 关闭模板资源
return outputStream.toByteArray();
}
}
} }

View File

@ -0,0 +1,15 @@
package org.dromara.design.domain.vo;
import lombok.Data;
@Data
public class DesCollectFileWordVo {
private Integer num;
private String fileName;
private String opinion;
}

View File

@ -0,0 +1,25 @@
package org.dromara.design.exportUtil.plan;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
@Data
@AllArgsConstructor
@NoArgsConstructor
public class AttachmentPersonnel {
String professional; // 专业及人员分工
String leaderName; // 专业负责人姓名
String leaderTitle; // 专业负责人职称
String designerName; // 设计人姓名
String designerTitle; // 设计人职称
String reviewerName; // 校审人姓名
String reviewerTitle; // 校审人职称
String checkerName; // 审核人姓名
String checkerTitle; // 审核人职称
String approverName; // 审定人姓名
String approverTitle; // 审定人职称
}

View File

@ -369,13 +369,14 @@ public class BusBillofquantitiesVersionsServiceImpl extends ServiceImpl<BusBillo
List<BusBillofquantities> dbList = busBillofquantitiesService.list(Wrappers.<BusBillofquantities>lambdaQuery() List<BusBillofquantities> dbList = busBillofquantitiesService.list(Wrappers.<BusBillofquantities>lambdaQuery()
.eq(BusBillofquantities::getVersions, versions) .eq(BusBillofquantities::getVersions, versions)
.eq(BusBillofquantities::getProjectId, projectId) .eq(BusBillofquantities::getProjectId, projectId)
.orderByAsc(BusBillofquantities::getId)
); );
if (CollectionUtil.isEmpty(dbList)) { if (CollectionUtil.isEmpty(dbList)) {
return Collections.emptyMap(); return Collections.emptyMap();
} }
// 2. 转换为导出实体并按sheet分组 // 2. 转换为导出实体并按sheet分组
Map<String, List<BillOfQuantitiesExport>> sheetMap = new HashMap<>(); Map<String, List<BillOfQuantitiesExport>> sheetMap = new LinkedHashMap<>();
for (BusBillofquantities dbItem : dbList) { for (BusBillofquantities dbItem : dbList) {
BillOfQuantitiesExport exportItem = new BillOfQuantitiesExport(); BillOfQuantitiesExport exportItem = new BillOfQuantitiesExport();
BeanUtil.copyProperties(dbItem, exportItem); BeanUtil.copyProperties(dbItem, exportItem);

View File

@ -1,39 +0,0 @@
package org.dromara.facility.domain.vo.matrix;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.dromara.progress.domain.vo.progresscategory.PgsProgressCategoryStructureVo;
import java.io.Serial;
import java.io.Serializable;
import java.util.List;
/**
* @author lilemy
* @date 2025-08-23 01:17
*/
@Data
@NoArgsConstructor
@AllArgsConstructor
public class FacMatrixStructureVo implements Serializable {
@Serial
private static final long serialVersionUID = 7526403047030009646L;
/**
* 主键
*/
private Long id;
/**
* 方阵名称
*/
private String name;
/**
* 分项工程
*/
private List<PgsProgressCategoryStructureVo> children;
}

View File

@ -847,7 +847,7 @@ public class FacPhotovoltaicPanelPartsServiceImpl implements IFacPhotovoltaicPan
// 根据类型,更新对应数据 // 根据类型,更新对应数据
if (type.equals(RecognizerTypeEnum.HOLE.getValue())) { if (type.equals(RecognizerTypeEnum.HOLE.getValue())) {
photovoltaicPanelPointService.updateFinishNumberByCoordinate(projectIds, matchPoints); photovoltaicPanelPointService.updateFinishNumberByCoordinate(projectIds, matchPoints);
} else if (type.equals(RecognizerTypeEnum.PILE.getValue())) { } else if (type.equals(RecognizerTypeEnum.COLUMN.getValue())) {
photovoltaicPanelColumnService.updateFinishNumberByCoordinate(projectIds, matchPoints); photovoltaicPanelColumnService.updateFinishNumberByCoordinate(projectIds, matchPoints);
} else if (type.equals(RecognizerTypeEnum.BRACKET.getValue())) { } else if (type.equals(RecognizerTypeEnum.BRACKET.getValue())) {
photovoltaicPanelSupportService.updateFinishNumberByCoordinate(projectIds, matchPoints); photovoltaicPanelSupportService.updateFinishNumberByCoordinate(projectIds, matchPoints);
@ -871,7 +871,7 @@ public class FacPhotovoltaicPanelPartsServiceImpl implements IFacPhotovoltaicPan
return list.stream().map(point -> return list.stream().map(point ->
new IdCoordinatePoint(point.getId(), point.getPositions())).toList(); new IdCoordinatePoint(point.getId(), point.getPositions())).toList();
} }
} else if (type.equals(RecognizerTypeEnum.PILE.getValue())) { } else if (type.equals(RecognizerTypeEnum.COLUMN.getValue())) {
List<FacPhotovoltaicPanelColumn> list = photovoltaicPanelColumnService.lambdaQuery() List<FacPhotovoltaicPanelColumn> list = photovoltaicPanelColumnService.lambdaQuery()
.in(FacPhotovoltaicPanelColumn::getProjectId, projectIds) .in(FacPhotovoltaicPanelColumn::getProjectId, projectIds)
.ne(FacPhotovoltaicPanelColumn::getStatus, FacFinishStatusEnum.FINISH.getValue()) .ne(FacPhotovoltaicPanelColumn::getStatus, FacFinishStatusEnum.FINISH.getValue())

View File

@ -23,7 +23,10 @@ import org.dromara.facility.constant.FacRedisKeyConstant;
import org.dromara.facility.domain.FacMatrix; import org.dromara.facility.domain.FacMatrix;
import org.dromara.facility.domain.FacPhotovoltaicPanel; import org.dromara.facility.domain.FacPhotovoltaicPanel;
import org.dromara.facility.domain.dto.geojson.*; import org.dromara.facility.domain.dto.geojson.*;
import org.dromara.facility.domain.dto.photovoltaicpanel.*; import org.dromara.facility.domain.dto.photovoltaicpanel.FacPhotovoltaicPanelCreateByGeoJsonReq;
import org.dromara.facility.domain.dto.photovoltaicpanel.FacPhotovoltaicPanelCreateReq;
import org.dromara.facility.domain.dto.photovoltaicpanel.FacPhotovoltaicPanelQueryReq;
import org.dromara.facility.domain.dto.photovoltaicpanel.FacPhotovoltaicPanelUpdateReq;
import org.dromara.facility.domain.enums.FacFinishStatusEnum; import org.dromara.facility.domain.enums.FacFinishStatusEnum;
import org.dromara.facility.domain.enums.FacFinishTypeEnum; import org.dromara.facility.domain.enums.FacFinishTypeEnum;
import org.dromara.facility.domain.vo.photovoltaicpanel.FacPhotovoltaicPanelVo; import org.dromara.facility.domain.vo.photovoltaicpanel.FacPhotovoltaicPanelVo;
@ -329,10 +332,10 @@ public class FacPhotovoltaicPanelServiceImpl extends ServiceImpl<FacPhotovoltaic
} }
Long matrixId = matrix.getId();*/ Long matrixId = matrix.getId();*/
// 去掉首字母 (T/G) // 去掉首字母 (T/G)
String withoutPrefix = name.substring(2); String withoutPrefix = name.substring(1);
// 如果包含".",只取第一个"."前的数字 // 如果包含".",只取第一个"."前的数字
int dotIndex = withoutPrefix.indexOf("#"); int dotIndex = withoutPrefix.indexOf(".");
if (dotIndex != -1) { if (dotIndex != -1) {
withoutPrefix = withoutPrefix.substring(0, dotIndex); withoutPrefix = withoutPrefix.substring(0, dotIndex);
} }

View File

@ -61,7 +61,7 @@ public class GpsEquipmentSonController extends BaseController {
/** /**
* 查询GPS设备定位日期信息列表 * 查询GPS设备定位日期信息列表
*/ */
@SaCheckPermission("gps:equipmentSon:getRlList") // @SaCheckPermission("gps:equipmentSon:getRlList")
@GetMapping("/getRlList") @GetMapping("/getRlList")
public R<List<GpsStatusVo>> getRlList(GpsEquipmentSonBo bo) { public R<List<GpsStatusVo>> getRlList(GpsEquipmentSonBo bo) {
return R.ok(gpsEquipmentSonService.getRlList(bo)); return R.ok(gpsEquipmentSonService.getRlList(bo));

View File

@ -81,31 +81,15 @@ public interface GpsEquipmentSonMapper extends BaseMapperPlus<GpsEquipmentSon, G
" rn = 1;") " rn = 1;")
List<GpsEquipmentSonVo> getUserListByProjectId(@Param("projectId") Long projectId, @Param("startTime") LocalDateTime startOfDay, @Param("endTime") LocalDateTime now); List<GpsEquipmentSonVo> getUserListByProjectId(@Param("projectId") Long projectId, @Param("startTime") LocalDateTime startOfDay, @Param("endTime") LocalDateTime now);
@Select("WITH RECURSIVE date_range AS (\n" + @Select("SELECT\n" +
" -- 1. 初始化开始日期取startTime的“年月日”部分忽略时分秒\n" + " DATE(create_time) AS riqi,\n" +
" SELECT DATE(#{bo.startTime}) AS stat_date\n" + " COUNT(id) AS count \n" +
" UNION ALL\n" + "FROM\n" +
" -- 2. 递归生成后续日期直到不超过endTime的“年月日”\n" + " gps_equipment_son\n" +
" SELECT DATE_ADD(stat_date, INTERVAL 1 DAY)\n" + "WHERE\n" +
" FROM date_range\n" + " project_id = #{bo.projectId}\n" +
" WHERE stat_date < DATE(#{bo.endTime})\n" + " AND client_id = #{bo.clientId}\n" +
")\n" + " AND create_time BETWEEN #{bo.startTime} AND #{bo.endTime}\n" +
"\n" + " GROUP BY DATE(create_time)")
"SELECT \n" +
" dr.stat_date AS riqi, -- 统计日期格式YYYY-MM-DD\n" +
" COUNT(ges.id) AS count -- 当天符合条件的记录数\n" +
"FROM date_range dr\n" +
"LEFT JOIN (\n" +
" SELECT \n" +
" DATE(create_time) AS data_date, -- 提取创建时间的“年月日”\n" +
" id -- 仅需主键用于计数(减少数据传输)\n" +
" FROM gps_equipment_son\n" +
" WHERE \n" +
" project_id = #{bo.projectId} -- 匹配项目ID\n" +
" AND client_id =#{bo.clientId} -- 客户端ID为空\n" +
" AND create_time BETWEEN #{bo.startTime} AND #{bo.endTime} -- 时间范围\n" +
") ges ON dr.stat_date = ges.data_date -- 按日期关联\n" +
"GROUP BY dr.stat_date -- 按统计日期分组\n" +
"ORDER BY dr.stat_date; -- 按日期升序排列")
List<GpsStatusVo> getRlList(@Param("bo") GpsEquipmentSonBo bo); List<GpsStatusVo> getRlList(@Param("bo") GpsEquipmentSonBo bo);
} }

View File

@ -4,6 +4,7 @@ package org.dromara.job.attendance;
import cn.hutool.core.collection.CollectionUtil; import cn.hutool.core.collection.CollectionUtil;
import cn.hutool.core.date.DateUtil; import cn.hutool.core.date.DateUtil;
import com.aizuda.snailjob.client.job.core.annotation.JobExecutor; import com.aizuda.snailjob.client.job.core.annotation.JobExecutor;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper; import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import jakarta.annotation.Resource; import jakarta.annotation.Resource;
@ -120,11 +121,23 @@ public class AttendanceJob {
// //查询项目下的关联人员 // //查询项目下的关联人员
// List<BusUserProjectRelevancy> relevancyList = userProjectRelevancyService.list(Wrappers.lambdaQuery(BusUserProjectRelevancy.class) // List<BusUserProjectRelevancy> relevancyList = userProjectRelevancyService.list(Wrappers.lambdaQuery(BusUserProjectRelevancy.class)
// .eq(BusUserProjectRelevancy::getProjectId, rule.getProjectId())); // .eq(BusUserProjectRelevancy::getProjectId, rule.getProjectId()));
List<SubConstructionUser> constructionUsers = constructionUserService.list(Wrappers.<SubConstructionUser>lambdaQuery() LambdaQueryWrapper<SubConstructionUser> queryWrapper = new LambdaQueryWrapper<>();
.eq(SubConstructionUser::getProjectId, rule.getProjectId())
.isNotNull(SubConstructionUser::getTeamId) // 拼接条件:(role = 1 AND teamId IS NOT NULL) OR (role IN (2))
.eq(SubConstructionUser::getUserRole, "0") //0-施工人员 1-管理人员 2-分包管理人员 queryWrapper.eq(SubConstructionUser::getProjectId, rule.getProjectId()) // 全局条件projectId必选
); // 外层nested包裹整个OR条件块
.nested(w ->
// 内层nested强制 (user_role=0 AND team_id IS NOT NULL) 作为一个整体
w.nested(inner -> inner
.eq(SubConstructionUser::getUserRole, "0")
.isNotNull(SubConstructionUser::getTeamId)
)
.or() // 连接两个子条件
.in(SubConstructionUser::getUserRole, Arrays.asList("1", "2"))
);
List<SubConstructionUser> constructionUsers = constructionUserService.list(queryWrapper);
//查询当天已打上班卡人员 //查询当天已打上班卡人员
@ -235,11 +248,23 @@ public class AttendanceJob {
//查询项目下的关联人员 //查询项目下的关联人员
// List<BusUserProjectRelevancy> relevancyList = userProjectRelevancyService.list(Wrappers.lambdaQuery(BusUserProjectRelevancy.class) // List<BusUserProjectRelevancy> relevancyList = userProjectRelevancyService.list(Wrappers.lambdaQuery(BusUserProjectRelevancy.class)
// .eq(BusUserProjectRelevancy::getProjectId, rule.getProjectId())); // .eq(BusUserProjectRelevancy::getProjectId, rule.getProjectId()));
List<SubConstructionUser> constructionUsers = constructionUserService.list(Wrappers.<SubConstructionUser>lambdaQuery() LambdaQueryWrapper<SubConstructionUser> queryWrapper = new LambdaQueryWrapper<>();
.eq(SubConstructionUser::getProjectId, rule.getProjectId())
.isNotNull(SubConstructionUser::getTeamId) // 拼接条件:(role = 1 AND teamId IS NOT NULL) OR (role IN (2))
.eq(SubConstructionUser::getUserRole, "0") //0-施工人员 1-管理人员 2-分包管理人员 queryWrapper.eq(SubConstructionUser::getProjectId, rule.getProjectId()) // 全局条件projectId必选
); // 外层nested包裹整个OR条件块
.nested(w ->
// 内层nested强制 (user_role=0 AND team_id IS NOT NULL) 作为一个整体
w.nested(inner -> inner
.eq(SubConstructionUser::getUserRole, "0")
.isNotNull(SubConstructionUser::getTeamId)
)
.or() // 连接两个子条件
.in(SubConstructionUser::getUserRole, Arrays.asList("1", "2"))
);
List<SubConstructionUser> constructionUsers = constructionUserService.list(queryWrapper);
//查询当天打卡人员 //查询当天打卡人员
List<BusAttendance> allAttendanceList = attendanceService.list(Wrappers.lambdaQuery(BusAttendance.class) List<BusAttendance> allAttendanceList = attendanceService.list(Wrappers.lambdaQuery(BusAttendance.class)
.eq(BusAttendance::getClockDate, date) .eq(BusAttendance::getClockDate, date)

View File

@ -1,45 +0,0 @@
package org.dromara.job.once;
import jakarta.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.dromara.manager.ys7manager.Ys7Manager;
import org.dromara.manager.ys7manager.vo.Ys7QueryDeviceResponseVo;
import org.dromara.other.service.IOthYs7DeviceService;
import org.springframework.boot.CommandLineRunner;
import org.springframework.stereotype.Component;
import java.util.List;
/**
* 同步摄像头设备数据
*
* @author lilemy
* @date 2025/6/13 11:08
*/
@Slf4j
@Component
public class FullSyncYs7DeviceData implements CommandLineRunner {
@Resource
private Ys7Manager ys7Manager;
@Resource
private IOthYs7DeviceService ys7DeviceService;
@Override
public void run(String... args) throws Exception {
log.info("开始同步摄像头设备数据");
try {
List<Ys7QueryDeviceResponseVo> ys7QueryDeviceList = ys7Manager.queryAllDeviceList();
Boolean result = ys7DeviceService.saveOrUpdateByDeviceList(ys7QueryDeviceList);
if (result) {
log.info("摄像头设备数据同步成功");
} else {
log.info("没有需要同步的设备");
}
} catch (Exception e) {
log.info("摄像头设备数据同步失败", e);
}
}
}

View File

@ -21,6 +21,7 @@ import java.net.URI;
import java.net.URISyntaxException; import java.net.URISyntaxException;
import java.net.URLConnection; import java.net.URLConnection;
import java.util.List; import java.util.List;
import java.util.Objects;
/** /**
* @author lilemy * @author lilemy
@ -82,7 +83,9 @@ public class RecognizerManager {
// 画矩形框 // 画矩形框
g.drawRect(x, y, w, h); g.drawRect(x, y, w, h);
// 写文字(类型 + 置信度) // 写文字(类型 + 置信度)
String label = target.getType() + " (" + String.format("%.2f", target.getScore()) + ")"; RecognizerTypeEnum recognizerTypeEnum = RecognizerTypeEnum.fromValue(target.getType());
String label = recognizerTypeEnum != null ? Objects.requireNonNull(recognizerTypeEnum).getText() : target.getType()
+ " (" + String.format("%.2f", target.getScore()) + ")";
g.drawString(label, x, y - 5); g.drawString(label, x, y - 5);
} }
g.dispose(); g.dispose();

View File

@ -12,15 +12,17 @@ import java.util.stream.Collectors;
@Getter @Getter
public enum RecognizerTypeEnum { public enum RecognizerTypeEnum {
HARDHAT("安全帽识别", "nohelmet", "1"), WEARING_ALL("穿戴安全帽反光衣", "wearingall", ""),
VEST("反光背心识别", "novest", ""), NO_EQUIPMENT("没穿安全帽反光衣", "noequipment", "1"),
SMOKING("吸烟识别", "smoking", "3"), NO_HELMET("有反光衣没安全帽", "nohelmet", ""),
FIRE("火焰识别", "fire", "16"), NO_VEST("有安全帽没反光衣", "novest", ""),
SMOKE("雾识别","smoke",""), SMOKE("", "smoke", "3"),
SOLAR("光伏板识别", "solar", ""), FIRE("火焰", "fire", "16"),
BRACKET("光伏板支架识别", "bracket", ""), SMOGGY("烟雾", "smoggy", ""),
PILE("光伏板立柱识别", "pile", ""), PANEL("光伏板", "solar", ""),
HOLE("", "hole", ""); BRACKET("光伏板支架", "bracket", ""),
COLUMN("光伏板桩", "column", ""),
HOLE("光伏板孔", "hole", "");
private final String text; private final String text;

View File

@ -26,16 +26,20 @@ import org.dromara.common.utils.DocumentUtil;
import org.dromara.materials.constants.MatMaterialsConstant; import org.dromara.materials.constants.MatMaterialsConstant;
import org.dromara.materials.domain.MatMaterialReceive; import org.dromara.materials.domain.MatMaterialReceive;
import org.dromara.materials.domain.MatMaterialReceiveItem; import org.dromara.materials.domain.MatMaterialReceiveItem;
import org.dromara.materials.domain.MatMaterials;
import org.dromara.materials.domain.MatMaterialsInventory;
import org.dromara.materials.domain.dto.materialreceive.MatMaterialReceiveCreateReq; import org.dromara.materials.domain.dto.materialreceive.MatMaterialReceiveCreateReq;
import org.dromara.materials.domain.dto.materialreceive.MatMaterialReceiveQueryReq; import org.dromara.materials.domain.dto.materialreceive.MatMaterialReceiveQueryReq;
import org.dromara.materials.domain.dto.materialreceive.MatMaterialReceiveUpdateReq; import org.dromara.materials.domain.dto.materialreceive.MatMaterialReceiveUpdateReq;
import org.dromara.materials.domain.dto.materialreceive.MatMaterialReceiveWordDto; import org.dromara.materials.domain.dto.materialreceive.MatMaterialReceiveWordDto;
import org.dromara.materials.domain.dto.materialreceiveitem.MatMaterialReceiveItemDto; import org.dromara.materials.domain.dto.materialreceiveitem.MatMaterialReceiveItemDto;
import org.dromara.materials.domain.dto.materialreceiveitem.MatMaterialReceiveItemWordDto; import org.dromara.materials.domain.dto.materialreceiveitem.MatMaterialReceiveItemWordDto;
import org.dromara.materials.domain.enums.MatMaterialsInventoryOutPutEnum;
import org.dromara.materials.domain.vo.materialreceive.MatMaterialReceiveVo; import org.dromara.materials.domain.vo.materialreceive.MatMaterialReceiveVo;
import org.dromara.materials.mapper.MatMaterialReceiveMapper; import org.dromara.materials.mapper.MatMaterialReceiveMapper;
import org.dromara.materials.service.IMatMaterialReceiveItemService; import org.dromara.materials.service.IMatMaterialReceiveItemService;
import org.dromara.materials.service.IMatMaterialReceiveService; import org.dromara.materials.service.IMatMaterialReceiveService;
import org.dromara.materials.service.IMatMaterialsInventoryService;
import org.dromara.materials.service.IMatMaterialsService; import org.dromara.materials.service.IMatMaterialsService;
import org.dromara.project.service.IBusProjectService; import org.dromara.project.service.IBusProjectService;
import org.dromara.system.domain.vo.SysOssVo; import org.dromara.system.domain.vo.SysOssVo;
@ -53,6 +57,7 @@ import java.nio.file.Files;
import java.nio.file.Path; import java.nio.file.Path;
import java.nio.file.Paths; import java.nio.file.Paths;
import java.util.*; import java.util.*;
import java.util.stream.Collectors;
import java.util.zip.ZipOutputStream; import java.util.zip.ZipOutputStream;
/** /**
@ -81,6 +86,9 @@ public class MatMaterialReceiveServiceImpl extends ServiceImpl<MatMaterialReceiv
@Resource @Resource
private IMatMaterialsService materialsService; private IMatMaterialsService materialsService;
@Resource
private IMatMaterialsInventoryService materialsInventoryService;
/** /**
* 查询物料接收单 * 查询物料接收单
* *
@ -366,12 +374,37 @@ public class MatMaterialReceiveServiceImpl extends ServiceImpl<MatMaterialReceiv
@Override @Override
@Transactional(rollbackFor = Exception.class) @Transactional(rollbackFor = Exception.class)
public Boolean deleteByIds(Collection<Long> ids) { public Boolean deleteByIds(Collection<Long> ids) {
List<MatMaterialReceive> receiveList = this.listByIds(ids);
List<MatMaterialReceiveItem> itemList = materialReceiveItemService.lambdaQuery() List<MatMaterialReceiveItem> itemList = materialReceiveItemService.lambdaQuery()
.in(MatMaterialReceiveItem::getReceiveId, ids) .in(MatMaterialReceiveItem::getReceiveId, ids)
.list(); .list();
if (CollUtil.isNotEmpty(itemList)) { if (CollUtil.isNotEmpty(itemList)) {
materialReceiveItemService.removeBatchByIds(itemList); materialReceiveItemService.removeBatchByIds(itemList);
} }
// 关联删除材料数据
Set<String> formCode = receiveList.stream().map(MatMaterialReceive::getFormCode).collect(Collectors.toSet());
List<MatMaterials> materials = materialsService.lambdaQuery()
.in(MatMaterials::getFormCode, formCode)
.list();
if (CollUtil.isNotEmpty(materials)) {
for (MatMaterials material : materials) {
List<MatMaterialsInventory> inventoryList = materialsInventoryService.lambdaQuery()
.eq(MatMaterialsInventory::getMaterialsId, material.getId())
.eq(MatMaterialsInventory::getOutPut, MatMaterialsInventoryOutPutEnum.OUT.getValue())
.list();
if (CollUtil.isNotEmpty(inventoryList)) {
throw new ServiceException("存在关联的库存数据,无法删除", HttpStatus.BAD_REQUEST);
}
Set<Long> materialIds = materials.stream().map(MatMaterials::getId).collect(Collectors.toSet());
List<MatMaterialsInventory> allInventoryList = materialsInventoryService.lambdaQuery()
.in(MatMaterialsInventory::getMaterialsId, materialIds)
.list();
if (CollUtil.isNotEmpty(allInventoryList)) {
materialsInventoryService.removeBatchByIds(allInventoryList);
}
}
materialsService.removeBatchByIds(materials);
}
return this.removeBatchByIds(ids); return this.removeBatchByIds(ids);
} }

View File

@ -668,11 +668,13 @@ public class MatMaterialsServiceImpl extends ServiceImpl<MatMaterialsMapper, Mat
BeanUtils.copyProperties(material, vo); BeanUtils.copyProperties(material, vo);
Long id = material.getId(); Long id = material.getId();
MatMaterialsInventory put = putMap.get(id); MatMaterialsInventory put = putMap.get(id);
vo.setSupplier(put.getRecipient()); if (put != null) {
vo.setInventoryId(put.getId()); vo.setSupplier(put.getRecipient());
vo.setNumber(put.getNumber()); vo.setInventoryId(put.getId());
vo.setOperator(put.getOperator()); vo.setNumber(put.getNumber());
vo.setEnterTime(put.getCreateTime()); vo.setOperator(put.getOperator());
vo.setEnterTime(put.getCreateTime());
}
if (CollUtil.isNotEmpty(outList)) { if (CollUtil.isNotEmpty(outList)) {
List<MatMaterialsInventory> outs = outList.stream() List<MatMaterialsInventory> outs = outList.stream()
.filter(inventory -> inventory.getMaterialsId().equals(id)) .filter(inventory -> inventory.getMaterialsId().equals(id))

View File

@ -5,6 +5,8 @@ import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Configuration;
import org.springframework.web.socket.server.standard.ServerEndpointExporter; import org.springframework.web.socket.server.standard.ServerEndpointExporter;
import java.util.stream.Stream;
@Configuration @Configuration
public class WebSocketConfig { public class WebSocketConfig {

View File

@ -220,7 +220,17 @@ public class OthYs7DeviceImgServiceImpl extends ServiceImpl<OthYs7DeviceImgMappe
othYs7DeviceImg.setDeviceName(img.getDeviceName()); othYs7DeviceImg.setDeviceName(img.getDeviceName());
othYs7DeviceImg.setUrl(ossUrl); othYs7DeviceImg.setUrl(ossUrl);
// 将抓取的图片进行识别 // 将抓取的图片进行识别
List<RecognizerTypeEnum> recTypes = List.of(RecognizerTypeEnum.HARDHAT, RecognizerTypeEnum.SMOKING, RecognizerTypeEnum.FIRE); // List<RecognizerTypeEnum> recTypes = List.of(RecognizerTypeEnum.NO_EQUIPMENT,
// RecognizerTypeEnum.NO_HELMET,
// RecognizerTypeEnum.NO_EQUIPMENT,
// RecognizerTypeEnum.NO_VEST,
// RecognizerTypeEnum.SMOKE,
// RecognizerTypeEnum.FIRE);
List<RecognizerTypeEnum> recTypes = List.of(
RecognizerTypeEnum.COLUMN,
RecognizerTypeEnum.PANEL,
RecognizerTypeEnum.BRACKET,
RecognizerTypeEnum.HOLE);
RecognizeVo recognizeVo = null; RecognizeVo recognizeVo = null;
try { try {
recognizeVo = recognizerManager.recognize(ossUrl, recTypes); recognizeVo = recognizerManager.recognize(ossUrl, recTypes);

View File

@ -9,6 +9,7 @@ import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.RequiredArgsConstructor; import lombok.RequiredArgsConstructor;
import org.dromara.contractor.domain.SubContractor;
import org.dromara.contractor.service.ISubContractorService; import org.dromara.contractor.service.ISubContractorService;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
import org.dromara.out.domain.bo.OutSettlementValueSubcontractBo; import org.dromara.out.domain.bo.OutSettlementValueSubcontractBo;
@ -59,7 +60,11 @@ public class OutSettlementValueSubcontractServiceImpl extends ServiceImpl<OutSet
LambdaQueryWrapper<OutSettlementValueSubcontract> lqw = buildQueryWrapper(bo); LambdaQueryWrapper<OutSettlementValueSubcontract> lqw = buildQueryWrapper(bo);
Page<OutSettlementValueSubcontractVo> result = baseMapper.selectVoPage(pageQuery.build(), lqw); Page<OutSettlementValueSubcontractVo> result = baseMapper.selectVoPage(pageQuery.build(), lqw);
result.getRecords().forEach(e -> { result.getRecords().forEach(e -> {
e.setContractorName(contractorService.queryById(e.getContractorId()).getName()); SubContractor contractor = contractorService.getById(e.getContractorId());
if(contractor != null) {
e.setContractorName(contractor.getName());
}
}); });
return TableDataInfo.build(result); return TableDataInfo.build(result);
} }

View File

@ -1,37 +0,0 @@
package org.dromara.progress.domain.vo.progresscategory;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import java.io.Serial;
import java.io.Serializable;
import java.util.List;
/**
* @author lilemy
* @date 2025-08-23 01:19
*/
@Data
@NoArgsConstructor
@AllArgsConstructor
public class PgsProgressCategoryStructureVo implements Serializable {
@Serial
private static final long serialVersionUID = -8392912623299656962L;
/**
* 主键id
*/
private Long id;
/**
* 类别名称
*/
private String name;
/**
* 子类别
*/
private List<PgsProgressCategoryStructureVo> children;
}

View File

@ -1149,8 +1149,8 @@ public class PgsProgressPlanDetailServiceImpl extends ServiceImpl<PgsProgressPla
} }
List<Long> projectIds = projects.stream().map(BusProject::getId).distinct().toList(); List<Long> projectIds = projects.stream().map(BusProject::getId).distinct().toList();
// 识别类型:洞、桩、架、架子 // 识别类型:洞、桩、架、架子
List<RecognizerTypeEnum> enumList = List.of(RecognizerTypeEnum.HOLE, RecognizerTypeEnum.SOLAR, List<RecognizerTypeEnum> enumList = List.of(RecognizerTypeEnum.HOLE, RecognizerTypeEnum.PANEL,
RecognizerTypeEnum.PILE, RecognizerTypeEnum.BRACKET); RecognizerTypeEnum.COLUMN, RecognizerTypeEnum.BRACKET);
// 调用识别算法 // 调用识别算法
RecognizeVo recognizeVo = null; RecognizeVo recognizeVo = null;
try { try {
@ -1187,10 +1187,10 @@ public class PgsProgressPlanDetailServiceImpl extends ServiceImpl<PgsProgressPla
} }
log.info("类型:{},识别到的设施:{},转换坐标:{}", type, value, coordinateList); log.info("类型:{},识别到的设施:{},转换坐标:{}", type, value, coordinateList);
// 处理对应设施 // 处理对应设施
if (type.equals(RecognizerTypeEnum.SOLAR.getValue())) { if (type.equals(RecognizerTypeEnum.PANEL.getValue())) {
photovoltaicPanelService.updateFinishNumberByCoordinate(projectIds, coordinateList); photovoltaicPanelService.updateFinishNumberByCoordinate(projectIds, coordinateList);
} else if (type.equals(RecognizerTypeEnum.HOLE.getValue()) } else if (type.equals(RecognizerTypeEnum.HOLE.getValue())
|| type.equals(RecognizerTypeEnum.PILE.getValue()) || type.equals(RecognizerTypeEnum.COLUMN.getValue())
|| type.equals(RecognizerTypeEnum.BRACKET.getValue())) { || type.equals(RecognizerTypeEnum.BRACKET.getValue())) {
photovoltaicPanelPartsService.updateFinishNumberByCoordinate(projectIds, coordinateList, type); photovoltaicPanelPartsService.updateFinishNumberByCoordinate(projectIds, coordinateList, type);
} else { } else {

View File

@ -162,6 +162,12 @@ public class PgsProgressPlanServiceImpl extends ServiceImpl<PgsProgressPlanMappe
Long id = progressPlan.getId(); Long id = progressPlan.getId();
List<PgsProgressPlanDetailCreateDto> detailList = req.getDetailList(); List<PgsProgressPlanDetailCreateDto> detailList = req.getDetailList();
if (CollUtil.isNotEmpty(detailList)) { if (CollUtil.isNotEmpty(detailList)) {
// 判断详情数量是否合法
boolean isAnyEmpty = detailList.stream()
.allMatch(detail -> detail.getPlanNumber().compareTo(BigDecimal.ZERO) <= 0);
if (isAnyEmpty) {
throw new ServiceException("新增进度计划详情失败,请进行均分", HttpStatus.BAD_REQUEST);
}
List<PgsProgressPlanDetail> newDetailList = detailList.stream().map(detail -> { List<PgsProgressPlanDetail> newDetailList = detailList.stream().map(detail -> {
PgsProgressPlanDetail progressPlanDetail = new PgsProgressPlanDetail(); PgsProgressPlanDetail progressPlanDetail = new PgsProgressPlanDetail();
BeanUtils.copyProperties(detail, progressPlanDetail); BeanUtils.copyProperties(detail, progressPlanDetail);

View File

@ -91,4 +91,17 @@ public class BusAttendanceMachineController extends BaseController {
@PathVariable Long[] ids) { @PathVariable Long[] ids) {
return toAjax(busAttendanceMachineService.deleteWithValidByIds(List.of(ids), true)); return toAjax(busAttendanceMachineService.deleteWithValidByIds(List.of(ids), true));
} }
/**
* 批量重新下发
*/
@SaCheckPermission("project:attendanceMachine:reissue")
@RepeatSubmit()
@PostMapping("/reissue/{ids}")
public R<Void> reissue(@NotEmpty(message = "主键不能为空")
@PathVariable Long[] ids){
busAttendanceMachineService.reissue(List.of(ids));
return R.ok("已开始执行,请稍后刷新");
}
} }

View File

@ -1,6 +1,7 @@
package org.dromara.project.controller; package org.dromara.project.controller;
import cn.dev33.satoken.annotation.SaCheckPermission; import cn.dev33.satoken.annotation.SaCheckPermission;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import jakarta.servlet.http.HttpServletResponse; import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.NotEmpty; import jakarta.validation.constraints.NotEmpty;
import jakarta.validation.constraints.NotNull; import jakarta.validation.constraints.NotNull;
@ -13,10 +14,12 @@ import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.mybatis.core.page.PageQuery; import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo; import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.web.core.BaseController; import org.dromara.common.web.core.BaseController;
import org.dromara.project.domain.BusProjectTeam;
import org.dromara.project.domain.dto.leave.BusLeaveManagerReviewReq; import org.dromara.project.domain.dto.leave.BusLeaveManagerReviewReq;
import org.dromara.project.domain.dto.leave.BusLeaveQueryReq; import org.dromara.project.domain.dto.leave.BusLeaveQueryReq;
import org.dromara.project.domain.vo.leave.BusLeaveVo; import org.dromara.project.domain.vo.leave.BusLeaveVo;
import org.dromara.project.service.IBusLeaveService; import org.dromara.project.service.IBusLeaveService;
import org.dromara.project.service.IBusProjectTeamService;
import org.springframework.validation.annotation.Validated; import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
@ -36,6 +39,8 @@ public class BusLeaveController extends BaseController {
private final IBusLeaveService busLeaveService; private final IBusLeaveService busLeaveService;
private final IBusProjectTeamService projectTeamService;
/** /**
* 查询施工人员请假申请列表 * 查询施工人员请假申请列表
*/ */
@ -91,4 +96,17 @@ public class BusLeaveController extends BaseController {
@PathVariable Long[] ids) { @PathVariable Long[] ids) {
return toAjax(busLeaveService.deleteWithValidByIds(List.of(ids), true)); return toAjax(busLeaveService.deleteWithValidByIds(List.of(ids), true));
} }
/**
* 获取项目下所有班组
*/
@GetMapping("/teamList")
public R<List<BusProjectTeam>> add(Long projectId) {
List<BusProjectTeam> list = projectTeamService.list(Wrappers.lambdaQuery(BusProjectTeam.class)
.select(BusProjectTeam::getId, BusProjectTeam::getTeamName)
.eq(BusProjectTeam::getProjectId, projectId)
);
return R.ok(list);
}
} }

View File

@ -1,6 +1,7 @@
package org.dromara.project.controller; package org.dromara.project.controller;
import cn.dev33.satoken.annotation.SaCheckPermission; import cn.dev33.satoken.annotation.SaCheckPermission;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import jakarta.servlet.http.HttpServletResponse; import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.NotEmpty; import jakarta.validation.constraints.NotEmpty;
import jakarta.validation.constraints.NotNull; import jakarta.validation.constraints.NotNull;
@ -13,9 +14,12 @@ import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.mybatis.core.page.PageQuery; import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo; import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.web.core.BaseController; import org.dromara.common.web.core.BaseController;
import org.dromara.project.domain.BusProjectTeam;
import org.dromara.project.domain.dto.reissuecard.BusReissueCardAddReq;
import org.dromara.project.domain.dto.reissuecard.BusReissueCardManagerReviewReq; import org.dromara.project.domain.dto.reissuecard.BusReissueCardManagerReviewReq;
import org.dromara.project.domain.dto.reissuecard.BusReissueCardQueryReq; import org.dromara.project.domain.dto.reissuecard.BusReissueCardQueryReq;
import org.dromara.project.domain.vo.reissuecard.BusReissueCardVo; import org.dromara.project.domain.vo.reissuecard.BusReissueCardVo;
import org.dromara.project.service.IBusProjectTeamService;
import org.dromara.project.service.IBusReissueCardService; import org.dromara.project.service.IBusReissueCardService;
import org.springframework.validation.annotation.Validated; import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*; import org.springframework.web.bind.annotation.*;
@ -36,6 +40,8 @@ public class BusReissueCardController extends BaseController {
private final IBusReissueCardService busReissueCardService; private final IBusReissueCardService busReissueCardService;
private final IBusProjectTeamService projectTeamService;
/** /**
* 查询施工人员补卡申请列表 * 查询施工人员补卡申请列表
*/ */
@ -91,4 +97,16 @@ public class BusReissueCardController extends BaseController {
@PathVariable Long[] ids) { @PathVariable Long[] ids) {
return toAjax(busReissueCardService.deleteWithValidByIds(List.of(ids), true)); return toAjax(busReissueCardService.deleteWithValidByIds(List.of(ids), true));
} }
/**
* 获取项目下所有班组
*/
@GetMapping("/teamList")
public R<List<BusProjectTeam>> add(Long projectId) {
List<BusProjectTeam> list = projectTeamService.list(Wrappers.lambdaQuery(BusProjectTeam.class)
.select(BusProjectTeam::getId, BusProjectTeam::getTeamName)
.eq(BusProjectTeam::getProjectId, projectId)
);
return R.ok(list);
}
} }

View File

@ -128,8 +128,8 @@ public class BusAttendanceAppController extends BaseController {
* 获取用户打卡异常记录 * 获取用户打卡异常记录
*/ */
@GetMapping("/getAbnormalAttendance/{projectId}") @GetMapping("/getAbnormalAttendance/{projectId}")
public TableDataInfo<BusAttendanceVo> getAbnormalAttendance(@NotNull @PathVariable("projectId") Long projectId, PageQuery pageQuery){ public TableDataInfo<BusAttendanceVo> getAbnormalAttendance(@NotNull @PathVariable("projectId") Long projectId,String handle, PageQuery pageQuery){
return attendanceService.getAbnormalAttendance(projectId,pageQuery); return attendanceService.getAbnormalAttendance(projectId,handle,pageQuery);
} }
/** /**

View File

@ -1,6 +1,8 @@
package org.dromara.project.domain.vo.project; package org.dromara.project.domain.vo.project;
import lombok.AllArgsConstructor;
import lombok.Data; import lombok.Data;
import lombok.NoArgsConstructor;
import java.io.Serial; import java.io.Serial;
import java.io.Serializable; import java.io.Serializable;
@ -11,6 +13,8 @@ import java.util.List;
* @date 2025-08-23 01:14 * @date 2025-08-23 01:14
*/ */
@Data @Data
@NoArgsConstructor
@AllArgsConstructor
public class BusProjectStructureVo implements Serializable { public class BusProjectStructureVo implements Serializable {
@Serial @Serial
@ -29,5 +33,5 @@ public class BusProjectStructureVo implements Serializable {
/** /**
* 子项目列表 * 子项目列表
*/ */
private List<BusSubProjectStructureVo> children; private List<BusProjectStructureVo> children;
} }

View File

@ -1,38 +0,0 @@
package org.dromara.project.domain.vo.project;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import org.dromara.facility.domain.vo.matrix.FacMatrixStructureVo;
import java.io.Serial;
import java.io.Serializable;
import java.util.List;
/**
* @author lilemy
* @date 2025-08-23 01:15
*/
@Data
@NoArgsConstructor
@AllArgsConstructor
public class BusSubProjectStructureVo implements Serializable {
@Serial
private static final long serialVersionUID = 6993209784456857540L;
/**
* 项目主键
*/
private Long id;
/**
* 项目名称
*/
private String name;
/**
* 方阵列表
*/
private List<FacMatrixStructureVo> children;
}

View File

@ -1,9 +1,12 @@
package org.dromara.project.mapper; package org.dromara.project.mapper;
import org.apache.ibatis.annotations.Param;
import org.dromara.project.domain.BusProjectTeam; import org.dromara.project.domain.BusProjectTeam;
import org.dromara.project.domain.vo.projectteam.BusProjectTeamVo; import org.dromara.project.domain.vo.projectteam.BusProjectTeamVo;
import org.dromara.common.mybatis.core.mapper.BaseMapperPlus; import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
import java.util.List;
/** /**
* 项目班组Mapper接口 * 项目班组Mapper接口
* *
@ -12,4 +15,5 @@ import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
*/ */
public interface BusProjectTeamMapper extends BaseMapperPlus<BusProjectTeam, BusProjectTeamVo> { public interface BusProjectTeamMapper extends BaseMapperPlus<BusProjectTeam, BusProjectTeamVo> {
List<BusProjectTeam> selectByPunchRangeIn(@Param("punchRangeList") List<String> punchRangeList);
} }

View File

@ -1,12 +1,15 @@
package org.dromara.project.service; package org.dromara.project.service;
import com.baomidou.mybatisplus.extension.service.IService; import com.baomidou.mybatisplus.extension.service.IService;
import jakarta.validation.constraints.NotEmpty;
import org.dromara.common.mybatis.core.page.PageQuery; import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo; import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.project.domain.BusAttendanceMachine; import org.dromara.project.domain.BusAttendanceMachine;
import org.dromara.project.domain.dto.attendancemachine.BusAttendanceMachineQueryReq; import org.dromara.project.domain.dto.attendancemachine.BusAttendanceMachineQueryReq;
import org.dromara.project.domain.dto.attendancemachine.BusAttendanceMachineUpdateReq; import org.dromara.project.domain.dto.attendancemachine.BusAttendanceMachineUpdateReq;
import org.dromara.project.domain.vo.BusAttendanceMachineVo; import org.dromara.project.domain.vo.BusAttendanceMachineVo;
import org.springframework.scheduling.annotation.Async;
import org.springframework.web.bind.annotation.PathVariable;
import java.util.Collection; import java.util.Collection;
import java.util.List; import java.util.List;
@ -75,4 +78,7 @@ public interface IBusAttendanceMachineService extends IService<BusAttendanceMach
* @return 是否删除成功 * @return 是否删除成功
*/ */
Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid); Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid);
void reissue(Collection<Long> ids);
} }

View File

@ -131,7 +131,7 @@ public interface IBusAttendanceService extends IService<BusAttendance>{
/** /**
* 获取用户打卡异常记录 * 获取用户打卡异常记录
*/ */
TableDataInfo<BusAttendanceVo> getAbnormalAttendance(@NotNull @PathVariable("projectId") Long projectId, PageQuery pageQuery); TableDataInfo<BusAttendanceVo> getAbnormalAttendance(Long projectId,String handle, PageQuery pageQuery);
/** /**
* 统计指定日期的打卡人员 * 统计指定日期的打卡人员

View File

@ -4,6 +4,7 @@ import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.IService; import com.baomidou.mybatisplus.extension.service.IService;
import jakarta.validation.constraints.NotNull; import jakarta.validation.constraints.NotNull;
import org.apache.ibatis.annotations.Param;
import org.dromara.common.mybatis.core.page.PageQuery; import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo; import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.project.domain.BusProjectTeam; import org.dromara.project.domain.BusProjectTeam;
@ -126,4 +127,6 @@ public interface IBusProjectTeamService extends IService<BusProjectTeam> {
Boolean deleteUserId(Long id,Long userId); Boolean deleteUserId(Long id,Long userId);
List<TeamManageVo> getManager(Long teamId); List<TeamManageVo> getManager(Long teamId);
List<BusProjectTeam> selectByPunchRangeIn(List<String> punchRangeList);
} }

View File

@ -1,6 +1,7 @@
package org.dromara.project.service.impl; package org.dromara.project.service.impl;
import cn.hutool.core.collection.CollUtil; import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
@ -28,13 +29,14 @@ import org.dromara.project.service.IBusAttendanceMachineService;
import org.dromara.project.service.IBusProjectService; import org.dromara.project.service.IBusProjectService;
import org.dromara.project.service.IBusProjectTeamMemberService; import org.dromara.project.service.IBusProjectTeamMemberService;
import org.dromara.project.service.IBusProjectTeamService; import org.dromara.project.service.IBusProjectTeamService;
import org.dromara.system.domain.vo.SysOssVo;
import org.dromara.system.service.ISysOssService;
import org.springframework.beans.BeanUtils; import org.springframework.beans.BeanUtils;
import org.springframework.context.annotation.Lazy;
import org.springframework.scheduling.annotation.Async;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
import java.util.Arrays; import java.util.*;
import java.util.Collection;
import java.util.List;
import java.util.Map;
import java.util.stream.Collectors; import java.util.stream.Collectors;
/** /**
@ -61,8 +63,14 @@ public class BusAttendanceMachineServiceImpl extends ServiceImpl<BusAttendanceMa
private DeviceMessageSender deviceMessageSender; private DeviceMessageSender deviceMessageSender;
@Resource @Resource
@Lazy
private ISubConstructionUserService constructionUserService; private ISubConstructionUserService constructionUserService;
@Resource
@Lazy
private ISysOssService ossService;
/** /**
* 查询考勤机 * 查询考勤机
* *
@ -300,4 +308,57 @@ public class BusAttendanceMachineServiceImpl extends ServiceImpl<BusAttendanceMa
} }
return baseMapper.deleteByIds(ids) > 0; return baseMapper.deleteByIds(ids) > 0;
} }
@Async
@Override
public void reissue(Collection<Long> ids) {
List<BusAttendanceMachine> busAttendanceMachines = baseMapper.selectByIds(ids);
for (BusAttendanceMachine machine : busAttendanceMachines) {
String sn = machine.getSn();
try {
deviceMessageSender.deleteAllUsers(sn);
} catch (Exception e) {
log.error("删除考勤人员异常", e);
}
String teams = machine.getTeams();
if (StrUtil.isBlank(teams)) {
continue;
}
List<Long> oldTeamIds = Arrays.stream(teams.split(","))
.map(Long::parseLong)
.distinct()
.toList();
List<Long> userIds = projectTeamMemberService.lambdaQuery()
.select(BusProjectTeamMember::getMemberId)
.in(BusProjectTeamMember::getTeamId, oldTeamIds)
.list()
.stream().map(BusProjectTeamMember::getMemberId)
.toList();
if (CollUtil.isEmpty(userIds)) {
continue;
}
List<SubConstructionUser> users = constructionUserService.lambdaQuery()
.in(SubConstructionUser::getSysUserId, userIds)
.list();
Map<Long, String> faceMap = new HashMap<>();
List<String> list = users.stream().map(SubConstructionUser::getFacePic).filter(StrUtil::isNotBlank).toList();
if (CollUtil.isNotEmpty(list)) {
//转成Long的集合
List<Long> list1 = list.stream().map(Long::parseLong).toList();
List<SysOssVo> sysOssVos = ossService.listByIds(list1);
faceMap = sysOssVos.stream().collect(Collectors.toMap(SysOssVo::getOssId, SysOssVo::getUrl));
}
for (SubConstructionUser user : users) {
String facePic = StrUtil.isBlank(user.getFacePic()) ? "" : faceMap.get(Long.valueOf(user.getFacePic()));
deviceMessageSender.sendPersonnelInformation(sn, user.getSysUserId().toString()
, user.getUserName(), facePic);
}
}
}
} }

View File

@ -333,10 +333,11 @@ public class BusAttendanceServiceImpl extends ServiceImpl<BusAttendanceMapper, B
} }
//打卡范围 //打卡范围
if (!checkInRange(req)) { if (!"1".equals(req.getSource())){
throw new ServiceException("打卡位置不在范围内", HttpStatus.ERROR); if (!checkInRange(req)) {
throw new ServiceException("打卡位置不在范围内", HttpStatus.ERROR);
}
} }
//用户信息校验 //用户信息校验
SubConstructionUser constructionUser = constructionUserService.getBySysUserId(userId); SubConstructionUser constructionUser = constructionUserService.getBySysUserId(userId);
if ("1".equals(constructionUser.getStatus())) { if ("1".equals(constructionUser.getStatus())) {
@ -353,7 +354,6 @@ public class BusAttendanceServiceImpl extends ServiceImpl<BusAttendanceMapper, B
throw new ServiceException("当前用户没有设置工资,禁止打卡", HttpStatus.ERROR); throw new ServiceException("当前用户没有设置工资,禁止打卡", HttpStatus.ERROR);
} }
} }
// 判断用户是否已经被拉黑 // 判断用户是否已经被拉黑
constructionBlacklistService.validUserInBlacklist(constructionUser.getSysUserId(), req.getProjectId()); constructionBlacklistService.validUserInBlacklist(constructionUser.getSysUserId(), req.getProjectId());
Boolean result = false; Boolean result = false;
@ -793,7 +793,7 @@ public class BusAttendanceServiceImpl extends ServiceImpl<BusAttendanceMapper, B
@Override @Override
public TableDataInfo<BusAttendanceVo> getAbnormalAttendance(Long projectId, PageQuery pageQuery) { public TableDataInfo<BusAttendanceVo> getAbnormalAttendance(Long projectId,String handle, PageQuery pageQuery) {
List<String> abnormalList = Arrays.asList(BusAttendanceClockStatusEnum.LATE.getValue(), List<String> abnormalList = Arrays.asList(BusAttendanceClockStatusEnum.LATE.getValue(),
BusAttendanceClockStatusEnum.LEAVEEARLY.getValue(), BusAttendanceClockStatusEnum.LEAVEEARLY.getValue(),
@ -810,6 +810,7 @@ public class BusAttendanceServiceImpl extends ServiceImpl<BusAttendanceMapper, B
IPage<BusAttendanceVo> busAttendanceVoIPage = baseMapper.selectVoPage(pageQuery.build(), Wrappers.lambdaQuery(BusAttendance.class) IPage<BusAttendanceVo> busAttendanceVoIPage = baseMapper.selectVoPage(pageQuery.build(), Wrappers.lambdaQuery(BusAttendance.class)
.eq(BusAttendance::getUserId, userId) .eq(BusAttendance::getUserId, userId)
.eq(StrUtil.isNotBlank(handle), BusAttendance::getHandle, handle)
.eq(b, BusAttendance::getProjectId, projectId) .eq(b, BusAttendance::getProjectId, projectId)
.in(BusAttendance::getClockStatus, abnormalList) .in(BusAttendance::getClockStatus, abnormalList)
.ge(BusAttendance::getClockDate, LocalDate.now().minusDays(29)) .ge(BusAttendance::getClockDate, LocalDate.now().minusDays(29))

View File

@ -603,7 +603,7 @@ public class BusLeaveServiceImpl extends ServiceImpl<BusLeaveMapper, BusLeave>
.eq(BusAttendance::getUserId, busLeave.getUserId()) .eq(BusAttendance::getUserId, busLeave.getUserId())
); );
for (BusAttendance attendance : list) { for (BusAttendance attendance : list) {
attendance.setClockStatus(BusAttendanceClockStatusEnum.LATE.getValue()); attendance.setClockStatus(BusAttendanceClockStatusEnum.LEAVE.getValue());
} }
if(!list.isEmpty()){ if(!list.isEmpty()){
attendanceService.updateBatchById(list); attendanceService.updateBatchById(list);
@ -619,7 +619,7 @@ public class BusLeaveServiceImpl extends ServiceImpl<BusLeaveMapper, BusLeave>
.eq(BusAttendance::getUserId, busLeave.getUserId()) .eq(BusAttendance::getUserId, busLeave.getUserId())
); );
for (BusAttendance attendance : list) { for (BusAttendance attendance : list) {
attendance.setClockStatus(BusAttendanceClockStatusEnum.LATE.getValue()); attendance.setClockStatus(BusAttendanceClockStatusEnum.LEAVE.getValue());
} }
if(!list.isEmpty()){ if(!list.isEmpty()){
attendanceService.updateBatchById(list); attendanceService.updateBatchById(list);
@ -635,7 +635,7 @@ public class BusLeaveServiceImpl extends ServiceImpl<BusLeaveMapper, BusLeave>
.eq(BusAttendance::getUserId, busLeave.getUserId()) .eq(BusAttendance::getUserId, busLeave.getUserId())
); );
for (BusAttendance attendance : list) { for (BusAttendance attendance : list) {
attendance.setClockStatus(BusAttendanceClockStatusEnum.LATE.getValue()); attendance.setClockStatus(BusAttendanceClockStatusEnum.LEAVE.getValue());
} }
if(!list.isEmpty()){ if(!list.isEmpty()){
attendanceService.updateBatchById(list); attendanceService.updateBatchById(list);

View File

@ -1,6 +1,8 @@
package org.dromara.project.service.impl; package org.dromara.project.service.impl;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl; import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import jakarta.annotation.Resource;
import org.dromara.common.core.exception.ServiceException;
import org.dromara.common.core.utils.MapstructUtils; import org.dromara.common.core.utils.MapstructUtils;
import org.dromara.common.core.utils.StringUtils; import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.mybatis.core.page.TableDataInfo; import org.dromara.common.mybatis.core.page.TableDataInfo;
@ -9,6 +11,9 @@ import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper; import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.RequiredArgsConstructor; import lombok.RequiredArgsConstructor;
import org.dromara.project.domain.BusProjectTeam;
import org.dromara.project.service.IBusProjectTeamService;
import org.springframework.context.annotation.Lazy;
import org.springframework.stereotype.Service; import org.springframework.stereotype.Service;
import org.dromara.project.domain.bo.BusProjectPunchrangeBo; import org.dromara.project.domain.bo.BusProjectPunchrangeBo;
import org.dromara.project.domain.vo.BusProjectPunchrangeVo; import org.dromara.project.domain.vo.BusProjectPunchrangeVo;
@ -16,9 +21,11 @@ import org.dromara.project.domain.BusProjectPunchrange;
import org.dromara.project.mapper.BusProjectPunchrangeMapper; import org.dromara.project.mapper.BusProjectPunchrangeMapper;
import org.dromara.project.service.IBusProjectPunchrangeService; import org.dromara.project.service.IBusProjectPunchrangeService;
import java.util.ArrayList;
import java.util.List; import java.util.List;
import java.util.Map; import java.util.Map;
import java.util.Collection; import java.util.Collection;
import java.util.stream.Collectors;
/** /**
* 项目打卡范围Service业务层处理 * 项目打卡范围Service业务层处理
@ -33,6 +40,10 @@ public class BusProjectPunchrangeServiceImpl extends ServiceImpl<BusProjectPunch
private final BusProjectPunchrangeMapper baseMapper; private final BusProjectPunchrangeMapper baseMapper;
@Resource
@Lazy
private IBusProjectTeamService busProjectTeamService;
/** /**
* 查询项目打卡范围 * 查询项目打卡范围
* *
@ -130,6 +141,13 @@ public class BusProjectPunchrangeServiceImpl extends ServiceImpl<BusProjectPunch
if(isValid){ if(isValid){
//TODO 做一些业务上的校验,判断是否需要校验 //TODO 做一些业务上的校验,判断是否需要校验
} }
List<String> idList = ids.stream()
.map(String::valueOf) // 核心:将 Long 转为 String
.collect(Collectors.toList());
List<BusProjectTeam> busProjectTeams = busProjectTeamService.selectByPunchRangeIn(idList);
if(!busProjectTeams.isEmpty()){
throw new ServiceException("项目打卡范围正在被使用,请先解除关联关系!" );
}
return baseMapper.deleteByIds(ids) > 0; return baseMapper.deleteByIds(ids) > 0;
} }
} }

View File

@ -38,14 +38,12 @@ import org.dromara.contractor.service.ISubContractorService;
import org.dromara.design.service.IDesTechnicalStandardService; import org.dromara.design.service.IDesTechnicalStandardService;
import org.dromara.facility.domain.FacMatrix; import org.dromara.facility.domain.FacMatrix;
import org.dromara.facility.domain.vo.matrix.FacMatrixBySubProjectVo; import org.dromara.facility.domain.vo.matrix.FacMatrixBySubProjectVo;
import org.dromara.facility.domain.vo.matrix.FacMatrixStructureVo;
import org.dromara.facility.service.IFacMatrixService; import org.dromara.facility.service.IFacMatrixService;
import org.dromara.manager.weathermanager.WeatherConstant; import org.dromara.manager.weathermanager.WeatherConstant;
import org.dromara.manager.weathermanager.WeatherManager; import org.dromara.manager.weathermanager.WeatherManager;
import org.dromara.manager.weathermanager.vo.WeatherVo; import org.dromara.manager.weathermanager.vo.WeatherVo;
import org.dromara.progress.domain.PgsProgressCategory; import org.dromara.progress.domain.PgsProgressCategory;
import org.dromara.progress.domain.enums.PgsRelevancyStructureEnum; import org.dromara.progress.domain.enums.PgsRelevancyStructureEnum;
import org.dromara.progress.domain.vo.progresscategory.PgsProgressCategoryStructureVo;
import org.dromara.progress.service.IPgsProgressCategoryService; import org.dromara.progress.service.IPgsProgressCategoryService;
import org.dromara.progress.service.IPgsProgressCategoryTemplateService; import org.dromara.progress.service.IPgsProgressCategoryTemplateService;
import org.dromara.project.constant.BusProjectConstant; import org.dromara.project.constant.BusProjectConstant;
@ -1023,8 +1021,8 @@ public class BusProjectServiceImpl extends ServiceImpl<BusProjectMapper, BusProj
.list(); .list();
// 构造子项目结构 // 构造子项目结构
List<BusSubProjectStructureVo> subProjectStructures = subProjects.stream().map(subProject -> { List<BusProjectStructureVo> subProjectStructures = new ArrayList<>(subProjects.stream().map(subProject -> {
BusSubProjectStructureVo subProjectVo = new BusSubProjectStructureVo(); BusProjectStructureVo subProjectVo = new BusProjectStructureVo();
subProjectVo.setId(subProject.getId()); subProjectVo.setId(subProject.getId());
subProjectVo.setName(subProject.getProjectName()); subProjectVo.setName(subProject.getProjectName());
@ -1054,22 +1052,22 @@ public class BusProjectServiceImpl extends ServiceImpl<BusProjectMapper, BusProj
.collect(Collectors.groupingBy(PgsProgressCategory::getParentId)); .collect(Collectors.groupingBy(PgsProgressCategory::getParentId));
} }
Map<Long, List<PgsProgressCategory>> finalSub3CategoryMap = sub3CategoryMap; Map<Long, List<PgsProgressCategory>> finalSub3CategoryMap = sub3CategoryMap;
List<FacMatrixStructureVo> structureVoList = sub1Category.stream() List<BusProjectStructureVo> structureVoList = sub1Category.stream()
.map(category -> { .map(category -> {
FacMatrixStructureVo matrixVo = new FacMatrixStructureVo(); BusProjectStructureVo matrixVo = new BusProjectStructureVo();
Long id = category.getId(); Long id = category.getId();
matrixVo.setId(id); matrixVo.setId(id);
matrixVo.setName(category.getName()); matrixVo.setName(category.getName());
if (CollUtil.isNotEmpty(finalSub2CategoryMap) && finalSub2CategoryMap.containsKey(id)) { if (CollUtil.isNotEmpty(finalSub2CategoryMap) && finalSub2CategoryMap.containsKey(id)) {
matrixVo.setChildren(finalSub2CategoryMap.get(id).stream() matrixVo.setChildren(finalSub2CategoryMap.get(id).stream()
.map(c -> { .map(c -> {
PgsProgressCategoryStructureVo subSubCategoryVo = new PgsProgressCategoryStructureVo(); BusProjectStructureVo subSubCategoryVo = new BusProjectStructureVo();
subSubCategoryVo.setId(c.getId()); subSubCategoryVo.setId(c.getId());
subSubCategoryVo.setName(c.getName()); subSubCategoryVo.setName(c.getName());
if (CollUtil.isNotEmpty(finalSub3CategoryMap) && finalSub3CategoryMap.containsKey(c.getId())) { if (CollUtil.isNotEmpty(finalSub3CategoryMap) && finalSub3CategoryMap.containsKey(c.getId())) {
subSubCategoryVo.setChildren(finalSub3CategoryMap.get(c.getId()).stream() subSubCategoryVo.setChildren(finalSub3CategoryMap.get(c.getId()).stream()
.map(c3 -> { .map(c3 -> {
PgsProgressCategoryStructureVo sub3CategoryVo = new PgsProgressCategoryStructureVo(); BusProjectStructureVo sub3CategoryVo = new BusProjectStructureVo();
sub3CategoryVo.setId(c3.getId()); sub3CategoryVo.setId(c3.getId());
sub3CategoryVo.setName(c3.getName()); sub3CategoryVo.setName(c3.getName());
return sub3CategoryVo; return sub3CategoryVo;
@ -1097,8 +1095,8 @@ public class BusProjectServiceImpl extends ServiceImpl<BusProjectMapper, BusProj
.list(); .list();
// 找到该子项目下的方阵 // 找到该子项目下的方阵
List<FacMatrix> matrices = matrixMap.getOrDefault(subProject.getId(), new ArrayList<>()); List<FacMatrix> matrices = matrixMap.getOrDefault(subProject.getId(), new ArrayList<>());
List<FacMatrixStructureVo> matrixVos = matrices.stream().map(matrix -> { List<BusProjectStructureVo> matrixVos = matrices.stream().map(matrix -> {
FacMatrixStructureVo matrixVo = new FacMatrixStructureVo(); BusProjectStructureVo matrixVo = new BusProjectStructureVo();
matrixVo.setId(matrix.getId()); matrixVo.setId(matrix.getId());
matrixVo.setName(matrix.getMatrixName()); matrixVo.setName(matrix.getMatrixName());
@ -1108,19 +1106,26 @@ public class BusProjectServiceImpl extends ServiceImpl<BusProjectMapper, BusProj
.toList(); .toList();
// 构造分项工程树 // 构造分项工程树
List<PgsProgressCategoryStructureVo> categoryTree = buildCategoryTree(categories); List<BusProjectStructureVo> categoryTree = buildCategoryTree(categories);
matrixVo.setChildren(categoryTree); matrixVo.setChildren(categoryTree);
return matrixVo; return matrixVo;
}).toList(); }).toList();
List<FacMatrixStructureVo> resultList = Stream.concat( List<BusProjectStructureVo> resultList = Stream.concat(
structureVoList.stream(), structureVoList.stream(),
matrixVos.stream() matrixVos.stream()
).toList(); ).toList();
subProjectVo.setChildren(resultList); subProjectVo.setChildren(resultList);
} }
return subProjectVo; return subProjectVo;
}).toList(); }).toList());
// 获取分项工程
List<PgsProgressCategory> progressCategoryList = progressCategoryService.lambdaQuery()
.eq(PgsProgressCategory::getRelevancyStructure, PgsRelevancyStructureEnum.PROJECT.getValue())
.in(PgsProgressCategory::getProjectId, projectId)
.list();
List<BusProjectStructureVo> projectStructureVos = this.buildCategoryTree(progressCategoryList);
subProjectStructures.addAll(projectStructureVos);
vo.setChildren(subProjectStructures); vo.setChildren(subProjectStructures);
return vo; return vo;
} }
@ -1252,159 +1257,159 @@ public class BusProjectServiceImpl extends ServiceImpl<BusProjectMapper, BusProj
// projectVos.add(create("台湾省", "台北", 25.0330, 121.5654, 1)); // projectVos.add(create("台湾省", "台北", 25.0330, 121.5654, 1));
// 1号项目 // 1号项目
projectVos.add(create("贵州省", "都匀市沙包堡匀东农业光伏电站项目", 26.2556, 107.5139, 1,"118.0452MWp")); projectVos.add(create("贵州省", "都匀市沙包堡匀东农业光伏电站项目", 26.2556, 107.5139, 1, "118.0452MWp"));
// 2号项目 // 2号项目
projectVos.add(create("贵州省", "长顺县朝核农业光伏电站", 26.1833, 106.4522, 1,"99.84MW")); projectVos.add(create("贵州省", "长顺县朝核农业光伏电站", 26.1833, 106.4522, 1, "99.84MW"));
// 3号项目 // 3号项目
projectVos.add(create("重庆市", "重庆无水港绿色低碳能源项目", 29.533155, 106.504962, 1,"2.598MW")); projectVos.add(create("重庆市", "重庆无水港绿色低碳能源项目", 29.533155, 106.504962, 1, "2.598MW"));
// 4号项目 // 4号项目
projectVos.add(create("贵州省", "兴义市捧乍猪场坪农业光伏电站项目", 25.1467, 104.8925, 1,"100MW")); projectVos.add(create("贵州省", "兴义市捧乍猪场坪农业光伏电站项目", 25.1467, 104.8925, 1, "100MW"));
// 5号项目 // 5号项目
projectVos.add(create("贵州省", "华能盘州市羊场高光村、松林农业光伏发电项目", 25.7833, 104.6583, 1,"200MW")); projectVos.add(create("贵州省", "华能盘州市羊场高光村、松林农业光伏发电项目", 25.7833, 104.6583, 1, "200MW"));
// 6号项目 // 6号项目
projectVos.add(create("贵州省", "大唐(六盘水)新能源有限公司水城区化乐农业光伏电站项目", 26.5167, 104.8289, 1,"99.84MW")); projectVos.add(create("贵州省", "大唐(六盘水)新能源有限公司水城区化乐农业光伏电站项目", 26.5167, 104.8289, 1, "99.84MW"));
// 7号项目 // 7号项目
projectVos.add(create("广西壮族自治区", "河池市宜州区北牙瑶族乡100MWp农光互补光伏发电项目", 24.6833, 108.6958, 1,"101.34MWp")); projectVos.add(create("广西壮族自治区", "河池市宜州区北牙瑶族乡100MWp农光互补光伏发电项目", 24.6833, 108.6958, 1, "101.34MWp"));
// 8号项目 // 8号项目
projectVos.add(create("四川省", "凉山木里茶布朗光伏发电项目220kV升压站设计施工总承包项目", 27.9167, 100.3250, 1,"220kV")); projectVos.add(create("四川省", "凉山木里茶布朗光伏发电项目220kV升压站设计施工总承包项目", 27.9167, 100.3250, 1, "220kV"));
// 9号项目 // 9号项目
projectVos.add(create("内蒙古自治区", "土默特右旗英能光伏电力开发有限公司100兆瓦光伏基地项目", 40.5333, 110.5489, 1,"100MWp")); projectVos.add(create("内蒙古自治区", "土默特右旗英能光伏电力开发有限公司100兆瓦光伏基地项目", 40.5333, 110.5489, 1, "100MWp"));
// 10号项目 // 10号项目
projectVos.add(create("云南省", "云南沾益农业光伏项目", 25.5000, 103.8194, 1,"350MWp")); projectVos.add(create("云南省", "云南沾益农业光伏项目", 25.5000, 103.8194, 1, "350MWp"));
// 11号项目 // 11号项目
projectVos.add(create("贵州省", "威宁县盐仓老鸦营30MW农业光伏电站项目", 26.8833, 104.2250, 1,"30MW")); projectVos.add(create("贵州省", "威宁县盐仓老鸦营30MW农业光伏电站项目", 26.8833, 104.2250, 1, "30MW"));
// 12号项目 // 12号项目
projectVos.add(create("云南省", "大黑土光伏电站总承包工程项目", 25.0406, 102.7142, 1,"272.97MW")); projectVos.add(create("云南省", "大黑土光伏电站总承包工程项目", 25.0406, 102.7142, 1, "272.97MW"));
// 13号项目 // 13号项目
projectVos.add(create("贵州省", "晴隆县碧痕新坪村风光火储一体化农业光伏电站", 25.5333, 105.1250, 1,"/")); projectVos.add(create("贵州省", "晴隆县碧痕新坪村风光火储一体化农业光伏电站", 25.5333, 105.1250, 1, "/"));
// 15号项目 // 15号项目
projectVos.add(create("河北省", "怀安县风光储一体化项目", 40.6667, 114.5417, 1,"200MW")); projectVos.add(create("河北省", "怀安县风光储一体化项目", 40.6667, 114.5417, 1, "200MW"));
// 16号项目 // 16号项目
projectVos.add(create("云南省", "保山市隆阳区黑岩洼光伏发电项目", 25.1250, 99.1667, 1,"100MW")); projectVos.add(create("云南省", "保山市隆阳区黑岩洼光伏发电项目", 25.1250, 99.1667, 1, "100MW"));
// 17号项目 // 17号项目
projectVos.add(create("云南省", "白玉光伏发电项目", 25.1250, 99.1667, 1,"340MW")); projectVos.add(create("云南省", "白玉光伏发电项目", 25.1250, 99.1667, 1, "340MW"));
// 20号项目 // 20号项目
projectVos.add(create("云南省", "云南省沾益区菱角农业光伏发电项目", 25.6000, 103.6833, 1,"350MWp")); projectVos.add(create("云南省", "云南省沾益区菱角农业光伏发电项目", 25.6000, 103.6833, 1, "350MWp"));
// 21号项目 // 21号项目
projectVos.add(create("云南省", "云南省文山州砚山县平远光伏发电项目", 23.7500, 104.3333, 1,"120MW")); projectVos.add(create("云南省", "云南省文山州砚山县平远光伏发电项目", 23.7500, 104.3333, 1, "120MW"));
// 22号项目 // 22号项目
projectVos.add(create("贵州省", "兴仁市大山能投农业光伏电站项目", 25.4000, 105.1833, 1,"100MW")); projectVos.add(create("贵州省", "兴仁市大山能投农业光伏电站项目", 25.4000, 105.1833, 1, "100MW"));
// 23号项目 // 23号项目
projectVos.add(create("贵州省", "兴仁市潘家庄能投农业光伏电站项目", 25.5333, 104.9833, 1,"100MW")); projectVos.add(create("贵州省", "兴仁市潘家庄能投农业光伏电站项目", 25.5333, 104.9833, 1, "100MW"));
// 47号项目 // 47号项目
projectVos.add(create("重庆市", "丰都许明寺镇100MW农牧光互补复合项目", 29.9333, 107.7500, 1,"100MW")); projectVos.add(create("重庆市", "丰都许明寺镇100MW农牧光互补复合项目", 29.9333, 107.7500, 1, "100MW"));
// 48号项目 // 48号项目
projectVos.add(create("云南省", "文山市茂克光伏电站项目", 23.3667, 104.2000, 1,"90.2MW")); projectVos.add(create("云南省", "文山市茂克光伏电站项目", 23.3667, 104.2000, 1, "90.2MW"));
// 50号项目 // 50号项目
projectVos.add(create("云南省", "文山市清水井光伏电站项目", 23.4500, 104.3333, 1,"120.25MW")); projectVos.add(create("云南省", "文山市清水井光伏电站项目", 23.4500, 104.3333, 1, "120.25MW"));
// 52号项目原序号1 // 52号项目原序号1
projectVos.add(create("广西壮族自治区", "新铝电力新山站屋顶分布式光伏发电项目EPC总承包", 22.8241, 108.3178, 1,"0.3MWp")); projectVos.add(create("广西壮族自治区", "新铝电力新山站屋顶分布式光伏发电项目EPC总承包", 22.8241, 108.3178, 1, "0.3MWp"));
// 53号项目原序号2 // 53号项目原序号2
projectVos.add(create("江西省", "江西省高速公路服务区分布式光伏项目EPC", 28.6764, 115.8922, 1,"120.12MWp")); projectVos.add(create("江西省", "江西省高速公路服务区分布式光伏项目EPC", 28.6764, 115.8922, 1, "120.12MWp"));
// 54号项目原序号3 // 54号项目原序号3
projectVos.add(create("河南省", "龙佰集团股份有限公司7MWp分布式光伏发电项目EPC总承包", 34.7573, 113.6145, 1,"8.4MWp")); projectVos.add(create("河南省", "龙佰集团股份有限公司7MWp分布式光伏发电项目EPC总承包", 34.7573, 113.6145, 1, "8.4MWp"));
// 55号项目原序号4 // 55号项目原序号4
projectVos.add(create("吉林省", "吉林热电检修安装工程有限公司吉林省南湖宾馆光储充一体化项目EPC总承包", 43.8868, 125.3245, 1,"400kW")); projectVos.add(create("吉林省", "吉林热电检修安装工程有限公司吉林省南湖宾馆光储充一体化项目EPC总承包", 43.8868, 125.3245, 1, "400kW"));
// 56号项目原序号5 // 56号项目原序号5
projectVos.add(create("吉林省", "集安市瀚能风电场相关装备有限公司益盛汉参集团分布式光伏发电项目EPC", 41.1333, 126.1650, 1,"3.50784MW")); projectVos.add(create("吉林省", "集安市瀚能风电场相关装备有限公司益盛汉参集团分布式光伏发电项目EPC", 41.1333, 126.1650, 1, "3.50784MW"));
// 57号项目原序号6 // 57号项目原序号6
projectVos.add(create("重庆市", "重庆潼南综合智慧零碳电厂耀辉环保单元项目", 30.1550, 106.2289, 1,"2.9MW")); projectVos.add(create("重庆市", "重庆潼南综合智慧零碳电厂耀辉环保单元项目", 30.1550, 106.2289, 1, "2.9MW"));
// 58号项目原序号7 // 58号项目原序号7
projectVos.add(create("重庆市", "汇智能源公司重庆永川综合智慧零碳电厂", 29.4167, 105.7833, 1,"2MW")); projectVos.add(create("重庆市", "汇智能源公司重庆永川综合智慧零碳电厂", 29.4167, 105.7833, 1, "2MW"));
// 59号项目原序号8 // 59号项目原序号8
projectVos.add(create("广西壮族自治区", "德保县乡村振兴光伏发电项目第二批EPC 总承包", 23.7167, 106.6833, 1,"44.775MW")); projectVos.add(create("广西壮族自治区", "德保县乡村振兴光伏发电项目第二批EPC 总承包", 23.7167, 106.6833, 1, "44.775MW"));
// 60号项目原序号9 // 60号项目原序号9
projectVos.add(create("重庆市", "汇智能源公司重庆永川综合智慧零碳电厂升科精锻单元项目工程EPC总承包工程一期", 29.4167, 105.7833, 1,"/")); projectVos.add(create("重庆市", "汇智能源公司重庆永川综合智慧零碳电厂升科精锻单元项目工程EPC总承包工程一期", 29.4167, 105.7833, 1, "/"));
// 62号项目原序号11 // 62号项目原序号11
projectVos.add(create("贵州省", "新铝电力莲塘、马隘变电站屋顶分布式光伏发电项目EPC工程总承包项目", 23.7833, 106.9500, 1,"0.788MW")); projectVos.add(create("贵州省", "新铝电力莲塘、马隘变电站屋顶分布式光伏发电项目EPC工程总承包项目", 23.7833, 106.9500, 1, "0.788MW"));
// 63号项目原序号12 // 63号项目原序号12
projectVos.add(create("广西壮族自治区", "广西德保县乡村振兴光伏发电项目第三批EPC总承包", 23.7167, 106.6833, 1,"191MW(直流侧装机容量243.9007MWp)")); projectVos.add(create("广西壮族自治区", "广西德保县乡村振兴光伏发电项目第三批EPC总承包", 23.7167, 106.6833, 1, "191MW(直流侧装机容量243.9007MWp)"));
// 64号项目原序号13 // 64号项目原序号13
projectVos.add(create("内蒙古自治区", "内蒙古自治区蒙西户用分布式200MW光伏发电项目EPC总承包四期", 40.6667, 109.8333, 1,"200MW")); projectVos.add(create("内蒙古自治区", "内蒙古自治区蒙西户用分布式200MW光伏发电项目EPC总承包四期", 40.6667, 109.8333, 1, "200MW"));
// 65号项目原序号14 // 65号项目原序号14
projectVos.add(create("广东省", "惠来县50MWp居民屋顶分布式光伏项目", 23.0333, 116.2833, 1,"50MWp")); projectVos.add(create("广东省", "惠来县50MWp居民屋顶分布式光伏项目", 23.0333, 116.2833, 1, "50MWp"));
// 66号项目原序号15 // 66号项目原序号15
projectVos.add(create("广西壮族自治区", "田东县乡村振兴分布式光伏发电项目二期EPC总承包", 23.6167, 106.9167, 1,"92MW")); projectVos.add(create("广西壮族自治区", "田东县乡村振兴分布式光伏发电项目二期EPC总承包", 23.6167, 106.9167, 1, "92MW"));
// 67号项目原序号16 // 67号项目原序号16
projectVos.add(create("广西壮族自治区", "田东县乡村振兴分布式光伏发电项目一期EPC总承包", 23.6167, 106.9167, 1,"203MW")); projectVos.add(create("广西壮族自治区", "田东县乡村振兴分布式光伏发电项目一期EPC总承包", 23.6167, 106.9167, 1, "203MW"));
// 68号项目原序号17 // 68号项目原序号17
projectVos.add(create("重庆市", "华能重庆华通电脑有限公司屋顶分布式光伏EPC项目合同", 29.533155, 106.504962, 1,"10.2245MWp")); projectVos.add(create("重庆市", "华能重庆华通电脑有限公司屋顶分布式光伏EPC项目合同", 29.533155, 106.504962, 1, "10.2245MWp"));
// 69号项目原序号18 // 69号项目原序号18
projectVos.add(create("广东省", "大埔峡能白罗20MW、长兴20MW、洋门10MW、群丰10MW农光互补光伏发电项目", 24.3667, 116.7000, 1,"60MWp")); projectVos.add(create("广东省", "大埔峡能白罗20MW、长兴20MW、洋门10MW、群丰10MW农光互补光伏发电项目", 24.3667, 116.7000, 1, "60MWp"));
// 70号项目原序号19 // 70号项目原序号19
projectVos.add(create("广东省", "化州区域分布式光伏项目", 21.7000, 110.6333, 1,"15MWp")); projectVos.add(create("广东省", "化州区域分布式光伏项目", 21.7000, 110.6333, 1, "15MWp"));
// 71号项目原序号20 // 71号项目原序号20
projectVos.add(create("河北省", "兴隆县10MW分布式光伏项目", 40.4167, 117.4833, 1,"5.99MW")); projectVos.add(create("河北省", "兴隆县10MW分布式光伏项目", 40.4167, 117.4833, 1, "5.99MW"));
// 75号项目原序号24 // 75号项目原序号24
projectVos.add(create("重庆市", "石柱发电公司厂区分布式光伏施工项目", 29.9333, 108.1333, 1,"0.9MW")); projectVos.add(create("重庆市", "石柱发电公司厂区分布式光伏施工项目", 29.9333, 108.1333, 1, "0.9MW"));
// 76号项目原序号25 // 76号项目原序号25
projectVos.add(create("陕西省", "靖边燃气发电厂3.0MW光伏发电工程", 37.6167, 108.7833, 1,"3MWp")); projectVos.add(create("陕西省", "靖边燃气发电厂3.0MW光伏发电工程", 37.6167, 108.7833, 1, "3MWp"));
// 77号项目原序号26 // 77号项目原序号26
projectVos.add(create("河北省", "河北兴隆 10MW分布式光伏项目", 40.4167, 117.4833, 1,"4MW")); projectVos.add(create("河北省", "河北兴隆 10MW分布式光伏项目", 40.4167, 117.4833, 1, "4MW"));
// 79号项目原序号28 // 79号项目原序号28
projectVos.add(create("广东省", "茂名分公司化工区物资仓库屋顶光伏发电合同能源管理项目", 21.6833, 110.8667, 1,"1.855MWp")); projectVos.add(create("广东省", "茂名分公司化工区物资仓库屋顶光伏发电合同能源管理项目", 21.6833, 110.8667, 1, "1.855MWp"));
// 88号项目原序号37 // 88号项目原序号37
projectVos.add(create("河北省", "怀安县风光储一体化项目", 40.6667, 114.5417, 1,"200MW")); projectVos.add(create("河北省", "怀安县风光储一体化项目", 40.6667, 114.5417, 1, "200MW"));
// 91号项目原序号2 // 91号项目原序号2
projectVos.add(create("辽宁省", "鑫泰新能源大石桥市200MW风电场新建工程项目", 40.6333, 122.5333, 2,"200MW")); projectVos.add(create("辽宁省", "鑫泰新能源大石桥市200MW风电场新建工程项目", 40.6333, 122.5333, 2, "200MW"));
// 92号项目原序号3 // 92号项目原序号3
projectVos.add(create("辽宁省", "大石桥市冠程新能源550MW风电场工程项目", 40.6333, 122.5333, 2,"550MW")); projectVos.add(create("辽宁省", "大石桥市冠程新能源550MW风电场工程项目", 40.6333, 122.5333, 2, "550MW"));
// 96号项目原序号7 // 96号项目原序号7
projectVos.add(create("四川省", "阿坝公司运检大楼“风光油储型”微电网试点项目", 31.9500, 102.2167, 2,"0.6MW")); projectVos.add(create("四川省", "阿坝公司运检大楼“风光油储型”微电网试点项目", 31.9500, 102.2167, 2, "0.6MW"));
// 老挝 - 万象 // 老挝 - 万象
projectVos.add(create("老挝", "巴塞", 15.110507, 105.817291, 1,"1000MW")); projectVos.add(create("老挝", "巴塞", 15.110507, 105.817291, 1, "1000MW"));
// 老挝 - 琅勃拉邦 // 老挝 - 琅勃拉邦
projectVos.add(create("老挝", "波利坎塞", 18.39639, 103.65583, 1,"50.1MW")); projectVos.add(create("老挝", "波利坎塞", 18.39639, 103.65583, 1, "50.1MW"));
Map<String, Map<String, Map<String, String>>> map = new HashMap<>(); Map<String, Map<String, Map<String, String>>> map = new HashMap<>();
for (SysDictDataVo projectType : projectTypes) { for (SysDictDataVo projectType : projectTypes) {
Map<String, Map<String, String>> map1 = new HashMap<>(); Map<String, Map<String, String>> map1 = new HashMap<>();
@ -1486,21 +1491,21 @@ public class BusProjectServiceImpl extends ServiceImpl<BusProjectMapper, BusProj
/** /**
* 构造分项工程树 * 构造分项工程树
*/ */
private List<PgsProgressCategoryStructureVo> buildCategoryTree(List<PgsProgressCategory> categories) { private List<BusProjectStructureVo> buildCategoryTree(List<PgsProgressCategory> categories) {
Map<Long, PgsProgressCategoryStructureVo> map = new HashMap<>(); Map<Long, BusProjectStructureVo> map = new HashMap<>();
List<PgsProgressCategoryStructureVo> roots = new ArrayList<>(); List<BusProjectStructureVo> roots = new ArrayList<>();
for (PgsProgressCategory c : categories) { for (PgsProgressCategory c : categories) {
PgsProgressCategoryStructureVo node = new PgsProgressCategoryStructureVo(c.getId(), c.getName(), new ArrayList<>()); BusProjectStructureVo node = new BusProjectStructureVo(c.getId(), c.getName(), new ArrayList<>());
map.put(c.getId(), node); map.put(c.getId(), node);
} }
for (PgsProgressCategory c : categories) { for (PgsProgressCategory c : categories) {
PgsProgressCategoryStructureVo node = map.get(c.getId()); BusProjectStructureVo node = map.get(c.getId());
if (c.getParentId() == 0) { if (c.getParentId() == 0) {
roots.add(node); roots.add(node);
} else { } else {
PgsProgressCategoryStructureVo parent = map.get(c.getParentId()); BusProjectStructureVo parent = map.get(c.getParentId());
if (parent != null) { if (parent != null) {
parent.getChildren().add(node); parent.getChildren().add(node);
} }
@ -1539,7 +1544,7 @@ public class BusProjectServiceImpl extends ServiceImpl<BusProjectMapper, BusProj
* @param projectType 项目类型 * @param projectType 项目类型
* @return 项目信息 * @return 项目信息
*/ */
private static BusProjectVo create(String province, String name, double lat, double lng, Integer projectType,String plan) { private static BusProjectVo create(String province, String name, double lat, double lng, Integer projectType, String plan) {
BusProjectVo vo = new BusProjectVo(); BusProjectVo vo = new BusProjectVo();
vo.setId(IdWorker.getID()); vo.setId(IdWorker.getID());
vo.setProvince(province); vo.setProvince(province);

View File

@ -17,6 +17,7 @@ import org.dromara.common.enums.AppUserTypeEnum;
import org.dromara.common.mybatis.core.page.PageQuery; import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo; import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.satoken.utils.LoginHelper; import org.dromara.common.satoken.utils.LoginHelper;
import org.dromara.common.utils.AsyncUtil;
import org.dromara.common.utils.IdCardEncryptorUtil; import org.dromara.common.utils.IdCardEncryptorUtil;
import org.dromara.contractor.domain.SubConstructionUser; import org.dromara.contractor.domain.SubConstructionUser;
import org.dromara.contractor.service.ISubConstructionUserService; import org.dromara.contractor.service.ISubConstructionUserService;
@ -90,6 +91,8 @@ public class BusProjectTeamMemberServiceImpl extends ServiceImpl<BusProjectTeamM
@Resource @Resource
private ISysOssService ossService; private ISysOssService ossService;
@Resource
private AsyncUtil asyncUtil;
/** /**
* 查询项目班组下的成员 * 查询项目班组下的成员
@ -219,6 +222,8 @@ public class BusProjectTeamMemberServiceImpl extends ServiceImpl<BusProjectTeamM
userService.updateFb(constructionUser.getSysUserId(),req.getContractorId(),false); userService.updateFb(constructionUser.getSysUserId(),req.getContractorId(),false);
} }
asyncUtil.sendPersonnel(req.getTeamId(), constructionUser);
return projectTeamMember.getId(); return projectTeamMember.getId();
} }
@ -356,6 +361,8 @@ public class BusProjectTeamMemberServiceImpl extends ServiceImpl<BusProjectTeamM
.set(SubConstructionUser::getTeamId, null) .set(SubConstructionUser::getTeamId, null)
.set(SubConstructionUser::getLeaveDate, new Date()); .set(SubConstructionUser::getLeaveDate, new Date());
constructionUserService.update(constructionUserLuw); constructionUserService.update(constructionUserLuw);
asyncUtil.deletePersonnel(constructionUser);
return true; return true;
} }

View File

@ -354,8 +354,6 @@ public class BusProjectTeamServiceImpl extends ServiceImpl<BusProjectTeamMapper,
projectTeamVo.setContractorName(subContractor.getName()); projectTeamVo.setContractorName(subContractor.getName());
} }
} }
// 获取班组人数 // 获取班组人数
Long peopleNumber = projectTeamMemberService.lambdaQuery() Long peopleNumber = projectTeamMemberService.lambdaQuery()
.eq(BusProjectTeamMember::getTeamId, projectTeam.getId()) .eq(BusProjectTeamMember::getTeamId, projectTeam.getId())
@ -475,7 +473,7 @@ public class BusProjectTeamServiceImpl extends ServiceImpl<BusProjectTeamMapper,
LambdaQueryWrapper<BusProjectTeam> lqw = new LambdaQueryWrapper<>(); LambdaQueryWrapper<BusProjectTeam> lqw = new LambdaQueryWrapper<>();
lqw.apply("FIND_IN_SET({0}, user_id) > 0", userId); lqw.apply("FIND_IN_SET({0}, user_id) > 0", userId);
lqw.eq(BusProjectTeam::getProjectId, projectId); lqw.eq(projectId!=null,BusProjectTeam::getProjectId, projectId);
List<BusProjectTeam> projectTeamList = list(lqw); List<BusProjectTeam> projectTeamList = list(lqw);
if (CollUtil.isNotEmpty(projectTeamList)) { if (CollUtil.isNotEmpty(projectTeamList)) {
return projectTeamList.stream().map(projectTeam -> { return projectTeamList.stream().map(projectTeam -> {
@ -539,4 +537,9 @@ public class BusProjectTeamServiceImpl extends ServiceImpl<BusProjectTeamMapper,
} }
return List.of(); return List.of();
} }
@Override
public List<BusProjectTeam> selectByPunchRangeIn(List<String> punchRangeList) {
return baseMapper.selectByPunchRangeIn(punchRangeList);
}
} }

View File

@ -213,6 +213,8 @@ public class HseSafetyLogServiceImpl extends ServiceImpl<HseSafetyLogMapper, Hse
if (CollUtil.isNotEmpty(sysUserVos)) { if (CollUtil.isNotEmpty(sysUserVos)) {
List<Long> userIds = sysUserVos.stream().map(SysUserVo::getUserId).toList(); List<Long> userIds = sysUserVos.stream().map(SysUserVo::getUserId).toList();
lqw.in(HseSafetyLog::getCreateBy, userIds); lqw.in(HseSafetyLog::getCreateBy, userIds);
}else {
lqw.eq(HseSafetyLog::getCreateBy, -1);
} }
} }
// 模糊查询 // 模糊查询

View File

@ -40,6 +40,8 @@ import org.dromara.design.service.IDesUserService;
import org.dromara.design.service.IDesVolumeCatalogService; import org.dromara.design.service.IDesVolumeCatalogService;
import org.dromara.design.service.IDesVolumeFileService; import org.dromara.design.service.IDesVolumeFileService;
import org.dromara.project.domain.BusUserProjectRelevancy; import org.dromara.project.domain.BusUserProjectRelevancy;
import org.dromara.project.domain.vo.projectteam.BusProjectTeamAppVo;
import org.dromara.project.service.IBusProjectTeamService;
import org.dromara.project.service.IBusUserProjectRelevancyService; import org.dromara.project.service.IBusUserProjectRelevancyService;
import org.dromara.system.domain.*; import org.dromara.system.domain.*;
import org.dromara.system.domain.bo.SysUserBo; import org.dromara.system.domain.bo.SysUserBo;
@ -108,6 +110,10 @@ public class SysUserServiceImpl implements ISysUserService, UserService {
@Resource @Resource
private ISysUserFileService userFileService; private ISysUserFileService userFileService;
@Lazy
@Resource
private IBusProjectTeamService projectTeamService;
@Override @Override
public TableDataInfo<SysUserVo> selectPageUserList(SysUserBo user, PageQuery pageQuery) { public TableDataInfo<SysUserVo> selectPageUserList(SysUserBo user, PageQuery pageQuery) {
Page<SysUserVo> page = baseMapper.selectPageUserList(pageQuery.build(), this.buildQueryWrapper(user)); Page<SysUserVo> page = baseMapper.selectPageUserList(pageQuery.build(), this.buildQueryWrapper(user));
@ -910,6 +916,14 @@ public class SysUserServiceImpl implements ISysUserService, UserService {
if(appUserType.equals(sysUser.getAppUserType())){ if(appUserType.equals(sysUser.getAppUserType())){
throw new ServiceException("当前已是选中用户类型 !"); throw new ServiceException("当前已是选中用户类型 !");
} }
String oldType = sysUser.getAppUserType();
if(AppUserTypeEnum.FB.getType().equals(oldType)){
List<BusProjectTeamAppVo> byUserId = projectTeamService.getByUserId(sysUser.getUserId(), null);
if (!byUserId.isEmpty()) {
throw new ServiceException("请先解除对班组的管理!");
}
}
Long contractorId = null; Long contractorId = null;
SubConstructionUser constructionUser = constructionUserService.lambdaQuery() SubConstructionUser constructionUser = constructionUserService.lambdaQuery()
.eq(SubConstructionUser::getSysUserId, userId) .eq(SubConstructionUser::getSysUserId, userId)
@ -924,7 +938,8 @@ public class SysUserServiceImpl implements ISysUserService, UserService {
); );
contractorId = constructionUser.getContractorId(); contractorId = constructionUser.getContractorId();
} }
String oldType = sysUser.getAppUserType();
if (AppUserTypeEnum.SG.getType().equals(oldType)) { //施工人员->管理人员/分包人员 if (AppUserTypeEnum.SG.getType().equals(oldType)) { //施工人员->管理人员/分包人员
//清除app所有角色 //清除app所有角色
userRoleMapper.deleteAppRoleByUserId(userId); userRoleMapper.deleteAppRoleByUserId(userId);
@ -967,6 +982,11 @@ public class SysUserServiceImpl implements ISysUserService, UserService {
relevancies.add(relevancy); relevancies.add(relevancy);
} }
userProjectRelevancyService.saveBatch(relevancies); userProjectRelevancyService.saveBatch(relevancies);
//然后取第一条数据赋值到实名认证表里
constructionUserService.lambdaUpdate()
.eq(SubConstructionUser::getSysUserId, userId)
.set(SubConstructionUser::getProjectId, projectIds.getFirst())
.update();
} }
return baseMapper.update(null, return baseMapper.update(null,

View File

@ -0,0 +1,118 @@
package org.dromara.vehicle.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.NotEmpty;
import jakarta.validation.constraints.NotNull;
import lombok.RequiredArgsConstructor;
import org.dromara.common.core.domain.R;
import org.dromara.common.excel.utils.ExcelUtil;
import org.dromara.common.idempotent.annotation.RepeatSubmit;
import org.dromara.common.log.annotation.Log;
import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.web.core.BaseController;
import org.dromara.vehicle.domain.dto.vehicleapply.VehVehicleApplyCreateReq;
import org.dromara.vehicle.domain.dto.vehicleapply.VehVehicleApplyQueryReq;
import org.dromara.vehicle.domain.dto.vehicleapply.VehVehicleApplyReviewReq;
import org.dromara.vehicle.domain.dto.vehicleapply.VehVehicleApplyUpdateReq;
import org.dromara.vehicle.domain.vo.VehVehicleApplyVo;
import org.dromara.vehicle.service.IVehVehicleApplyService;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import java.util.List;
/**
* 乘车申请
*
* @author lilemy
* @date 2025-10-25
*/
@Validated
@RequiredArgsConstructor
@RestController
@RequestMapping("/vehicle/vehicleApply")
public class VehVehicleApplyController extends BaseController {
private final IVehVehicleApplyService vehVehicleApplyService;
/**
* 查询乘车申请列表
*/
@SaCheckPermission("vehicle:vehicleApply:list")
@GetMapping("/list")
public TableDataInfo<VehVehicleApplyVo> list(VehVehicleApplyQueryReq req, PageQuery pageQuery) {
return vehVehicleApplyService.queryPageList(req, pageQuery);
}
/**
* 导出乘车申请列表
*/
@SaCheckPermission("vehicle:vehicleApply:export")
@Log(title = "乘车申请", businessType = BusinessType.EXPORT)
@PostMapping("/export")
public void export(VehVehicleApplyQueryReq req, HttpServletResponse response) {
List<VehVehicleApplyVo> list = vehVehicleApplyService.queryList(req);
ExcelUtil.exportExcel(list, "乘车申请", VehVehicleApplyVo.class, response);
}
/**
* 获取乘车申请详细信息
*
* @param id 主键
*/
@SaCheckPermission("vehicle:vehicleApply:query")
@GetMapping("/{id}")
public R<VehVehicleApplyVo> getInfo(@NotNull(message = "主键不能为空")
@PathVariable Long id) {
return R.ok(vehVehicleApplyService.queryById(id));
}
/**
* 新增乘车申请
*/
@SaCheckPermission("vehicle:vehicleApply:add")
@Log(title = "乘车申请", businessType = BusinessType.INSERT)
@RepeatSubmit()
@PostMapping()
public R<Void> add(@Validated @RequestBody VehVehicleApplyCreateReq req) {
return toAjax(vehVehicleApplyService.insertByBo(req));
}
/**
* 修改乘车申请
*/
@SaCheckPermission("vehicle:vehicleApply:edit")
@Log(title = "乘车申请", businessType = BusinessType.UPDATE)
@RepeatSubmit()
@PutMapping()
public R<Void> edit(@Validated @RequestBody VehVehicleApplyUpdateReq req) {
return toAjax(vehVehicleApplyService.updateByBo(req));
}
/**
* 车主审核
*/
@SaCheckPermission("vehicle:vehicleApply:edit")
@Log(title = "乘车申请", businessType = BusinessType.UPDATE)
@RepeatSubmit()
@PutMapping("/vehicleOwnerReview")
public R<Void> vehicleOwnerReview(@Validated @RequestBody VehVehicleApplyReviewReq req) {
return toAjax(vehVehicleApplyService.vehicleOwnerReview(req));
}
/**
* 删除乘车申请
*
* @param ids 主键串
*/
@SaCheckPermission("vehicle:vehicleApply:remove")
@Log(title = "乘车申请", businessType = BusinessType.DELETE)
@DeleteMapping("/{ids}")
public R<Void> remove(@NotEmpty(message = "主键不能为空")
@PathVariable Long[] ids) {
return toAjax(vehVehicleApplyService.deleteWithValidByIds(List.of(ids), true));
}
}

View File

@ -0,0 +1,106 @@
package org.dromara.vehicle.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.NotEmpty;
import jakarta.validation.constraints.NotNull;
import lombok.RequiredArgsConstructor;
import org.dromara.common.core.domain.R;
import org.dromara.common.core.validate.AddGroup;
import org.dromara.common.core.validate.EditGroup;
import org.dromara.common.excel.utils.ExcelUtil;
import org.dromara.common.idempotent.annotation.RepeatSubmit;
import org.dromara.common.log.annotation.Log;
import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.web.core.BaseController;
import org.dromara.vehicle.domain.bo.VehVehicleInfoBo;
import org.dromara.vehicle.domain.vo.VehVehicleInfoVo;
import org.dromara.vehicle.service.IVehVehicleInfoService;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import java.util.List;
/**
* 车辆信息
*
* @author lilemy
* @date 2025-10-25
*/
@Validated
@RequiredArgsConstructor
@RestController
@RequestMapping("/vehicle/vehicleInfo")
public class VehVehicleInfoController extends BaseController {
private final IVehVehicleInfoService vehVehicleInfoService;
/**
* 查询车辆信息列表
*/
@SaCheckPermission("vehicle:vehicleInfo:list")
@GetMapping("/list")
public TableDataInfo<VehVehicleInfoVo> list(VehVehicleInfoBo bo, PageQuery pageQuery) {
return vehVehicleInfoService.queryPageList(bo, pageQuery);
}
/**
* 导出车辆信息列表
*/
@SaCheckPermission("vehicle:vehicleInfo:export")
@Log(title = "车辆信息", businessType = BusinessType.EXPORT)
@PostMapping("/export")
public void export(VehVehicleInfoBo bo, HttpServletResponse response) {
List<VehVehicleInfoVo> list = vehVehicleInfoService.queryList(bo);
ExcelUtil.exportExcel(list, "车辆信息", VehVehicleInfoVo.class, response);
}
/**
* 获取车辆信息详细信息
*
* @param id 主键
*/
@SaCheckPermission("vehicle:vehicleInfo:query")
@GetMapping("/{id}")
public R<VehVehicleInfoVo> getInfo(@NotNull(message = "主键不能为空")
@PathVariable Long id) {
return R.ok(vehVehicleInfoService.queryById(id));
}
/**
* 新增车辆信息
*/
@SaCheckPermission("vehicle:vehicleInfo:add")
@Log(title = "车辆信息", businessType = BusinessType.INSERT)
@RepeatSubmit()
@PostMapping()
public R<Void> add(@Validated(AddGroup.class) @RequestBody VehVehicleInfoBo bo) {
return toAjax(vehVehicleInfoService.insertByBo(bo));
}
/**
* 修改车辆信息
*/
@SaCheckPermission("vehicle:vehicleInfo:edit")
@Log(title = "车辆信息", businessType = BusinessType.UPDATE)
@RepeatSubmit()
@PutMapping()
public R<Void> edit(@Validated(EditGroup.class) @RequestBody VehVehicleInfoBo bo) {
return toAjax(vehVehicleInfoService.updateByBo(bo));
}
/**
* 删除车辆信息
*
* @param ids 主键串
*/
@SaCheckPermission("vehicle:vehicleInfo:remove")
@Log(title = "车辆信息", businessType = BusinessType.DELETE)
@DeleteMapping("/{ids}")
public R<Void> remove(@NotEmpty(message = "主键不能为空")
@PathVariable Long[] ids) {
return toAjax(vehVehicleInfoService.deleteWithValidByIds(List.of(ids), true));
}
}

View File

@ -0,0 +1,118 @@
package org.dromara.vehicle.controller;
import cn.dev33.satoken.annotation.SaCheckPermission;
import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.NotEmpty;
import jakarta.validation.constraints.NotNull;
import lombok.RequiredArgsConstructor;
import org.dromara.common.core.domain.R;
import org.dromara.common.excel.utils.ExcelUtil;
import org.dromara.common.idempotent.annotation.RepeatSubmit;
import org.dromara.common.log.annotation.Log;
import org.dromara.common.log.enums.BusinessType;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.web.core.BaseController;
import org.dromara.vehicle.domain.dto.vehicletrip.VehVehicleTripCancelReq;
import org.dromara.vehicle.domain.dto.vehicletrip.VehVehicleTripCreateReq;
import org.dromara.vehicle.domain.dto.vehicletrip.VehVehicleTripQueryReq;
import org.dromara.vehicle.domain.dto.vehicletrip.VehVehicleTripUpdateReq;
import org.dromara.vehicle.domain.vo.VehVehicleTripVo;
import org.dromara.vehicle.service.IVehVehicleTripService;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import java.util.List;
/**
* 车辆出行记录
*
* @author lilemy
* @date 2025-10-25
*/
@Validated
@RequiredArgsConstructor
@RestController
@RequestMapping("/vehicle/vehicleTrip")
public class VehVehicleTripController extends BaseController {
private final IVehVehicleTripService vehVehicleTripService;
/**
* 查询车辆出行记录列表
*/
@SaCheckPermission("vehicle:vehicleTrip:list")
@GetMapping("/list")
public TableDataInfo<VehVehicleTripVo> list(VehVehicleTripQueryReq req, PageQuery pageQuery) {
return vehVehicleTripService.queryPageList(req, pageQuery);
}
/**
* 导出车辆出行记录列表
*/
@SaCheckPermission("vehicle:vehicleTrip:export")
@Log(title = "车辆出行记录", businessType = BusinessType.EXPORT)
@PostMapping("/export")
public void export(VehVehicleTripQueryReq req, HttpServletResponse response) {
List<VehVehicleTripVo> list = vehVehicleTripService.queryList(req);
ExcelUtil.exportExcel(list, "车辆出行记录", VehVehicleTripVo.class, response);
}
/**
* 获取车辆出行记录详细信息
*
* @param id 主键
*/
@SaCheckPermission("vehicle:vehicleTrip:query")
@GetMapping("/{id}")
public R<VehVehicleTripVo> getInfo(@NotNull(message = "主键不能为空")
@PathVariable Long id) {
return R.ok(vehVehicleTripService.queryById(id));
}
/**
* 新增车辆出行记录
*/
@SaCheckPermission("vehicle:vehicleTrip:add")
@Log(title = "车辆出行记录", businessType = BusinessType.INSERT)
@RepeatSubmit()
@PostMapping()
public R<Void> add(@Validated @RequestBody VehVehicleTripCreateReq req) {
return toAjax(vehVehicleTripService.insertByBo(req));
}
/**
* 修改车辆出行记录
*/
@SaCheckPermission("vehicle:vehicleTrip:edit")
@Log(title = "车辆出行记录", businessType = BusinessType.UPDATE)
@RepeatSubmit()
@PutMapping()
public R<Void> edit(@Validated @RequestBody VehVehicleTripUpdateReq req) {
return toAjax(vehVehicleTripService.updateByBo(req));
}
/**
* 取消车辆出行记录
*/
@SaCheckPermission("vehicle:vehicleTrip:edit")
@Log(title = "车辆出行记录", businessType = BusinessType.UPDATE)
@RepeatSubmit()
@PutMapping("/cancel")
public R<Void> cancel(@Validated @RequestBody VehVehicleTripCancelReq req) {
return toAjax(vehVehicleTripService.cancel(req));
}
/**
* 删除车辆出行记录
*
* @param ids 主键串
*/
@SaCheckPermission("vehicle:vehicleTrip:remove")
@Log(title = "车辆出行记录", businessType = BusinessType.DELETE)
@DeleteMapping("/{ids}")
public R<Void> remove(@NotEmpty(message = "主键不能为空")
@PathVariable Long[] ids) {
return toAjax(vehVehicleTripService.deleteWithValidByIds(List.of(ids), true));
}
}

View File

@ -0,0 +1,91 @@
package org.dromara.vehicle.domain;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;
import lombok.EqualsAndHashCode;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import java.io.Serial;
/**
* 乘车申请对象 veh_vehicle_apply
*
* @author lilemy
* @date 2025-10-25
*/
@Data
@EqualsAndHashCode(callSuper = true)
@TableName("veh_vehicle_apply")
public class VehVehicleApply extends BaseEntity {
@Serial
private static final long serialVersionUID = 1L;
/**
* 主键ID
*/
@TableId(value = "id")
private Long id;
/**
* 项目ID
*/
private Long projectId;
/**
* 关联行程ID
*/
private Long tripId;
/**
* 申请人数
*/
private Integer peopleNum;
/**
* 联系电话
*/
private String passengerPhone;
/**
* 出发地
*/
private String startPlace;
/**
* 目的地
*/
private String endPlace;
/**
* 出发地经度
*/
private String startLat;
/**
* 出发地纬度
*/
private String startLng;
/**
* 目的地经度
*/
private String endLat;
/**
* 目的地纬度
*/
private String endLng;
/**
* 乘车状态
*/
private String status;
/**
* 备注
*/
private String remark;
}

View File

@ -0,0 +1,148 @@
package org.dromara.vehicle.domain;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;
import lombok.EqualsAndHashCode;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import java.io.Serial;
import java.math.BigDecimal;
import java.time.LocalDate;
/**
* 车辆信息对象 veh_vehicle_info
*
* @author lilemy
* @date 2025-10-25
*/
@Data
@EqualsAndHashCode(callSuper = true)
@TableName("veh_vehicle_info")
public class VehVehicleInfo extends BaseEntity {
@Serial
private static final long serialVersionUID = 1L;
/**
* 主键ID
*/
@TableId(value = "id")
private Long id;
/**
* 项目ID
*/
private Long projectId;
/**
* 车牌号
*/
private String plateNumber;
/**
* 车辆品牌
*/
private String vehicleBrand;
/**
* 车辆类型
*/
private String vehicleType;
/**
* 车辆颜色
*/
private String vehicleColor;
/**
* 座位数
*/
private Integer seatCount;
/**
* 燃料类型
*/
private String fuelType;
/**
* 车辆状态
*/
private String vehicleStatus;
/**
* 车长(米)
*/
private BigDecimal vehicleLength;
/**
* 车宽(米)
*/
private BigDecimal vehicleWidth;
/**
* 车高(米)
*/
private BigDecimal vehicleHeight;
/**
* 轴距(米)
*/
private BigDecimal wheelBase;
/**
* 轮距(米)
*/
private BigDecimal wheelTrack;
/**
* 车辆性质
*/
private String ownerType;
/**
* 租赁方信息
*/
private String rentalCompany;
/**
* 登记证书编号(车管所登记凭证)
*/
private String registrationCertNo;
/**
* 登记日期
*/
private LocalDate registerDate;
/**
* 购置日期
*/
private LocalDate purchaseDate;
/**
* 购置价格
*/
private BigDecimal purchasePrice;
/**
* 保险到期时间
*/
private LocalDate insuranceExpiry;
/**
* 年检到期时间
*/
private LocalDate inspectionExpiry;
/**
* 附件ID
*/
private String fileIds;
/**
* 备注
*/
private String remark;
}

View File

@ -0,0 +1,122 @@
package org.dromara.vehicle.domain;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import lombok.Data;
import lombok.EqualsAndHashCode;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import java.io.Serial;
import java.util.Date;
/**
* 车辆出行记录对象 veh_vehicle_trip
*
* @author lilemy
* @date 2025-10-25
*/
@Data
@EqualsAndHashCode(callSuper = true)
@TableName("veh_vehicle_trip")
public class VehVehicleTrip extends BaseEntity {
@Serial
private static final long serialVersionUID = 1L;
/**
* 主键ID
*/
@TableId(value = "id")
private Long id;
/**
* 项目ID
*/
private Long projectId;
/**
* 车辆ID
*/
private Long vehicleId;
/**
* 车牌号
*/
private String plateNumber;
/**
* 联系电话
*/
private String passengerPhone;
/**
* 出行事由
*/
private String tripReason;
/**
* 出发地
*/
private String startPlace;
/**
* 目的地
*/
private String endPlace;
/**
* 出发地经度
*/
private String startLat;
/**
* 出发地纬度
*/
private String startLng;
/**
* 目的地经度
*/
private String endLat;
/**
* 目的地纬度
*/
private String endLng;
/**
* 计划出发时间
*/
private Date startTime;
/**
* 计划到达时间
*/
private Date endTime;
/**
* 申请人数
*/
private Integer peopleNum;
/**
* 剩余座位数
*/
private Integer leftSeat;
/**
* 审核状态
*/
private String reviewStatus;
/**
* 状态
*/
private String tripStatus;
/**
* 备注
*/
private String remark;
}

View File

@ -0,0 +1,158 @@
package org.dromara.vehicle.domain.bo;
import io.github.linpeilie.annotations.AutoMapper;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import lombok.EqualsAndHashCode;
import org.dromara.common.core.validate.AddGroup;
import org.dromara.common.core.validate.EditGroup;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import org.dromara.vehicle.domain.VehVehicleInfo;
import java.math.BigDecimal;
import java.time.LocalDate;
/**
* 车辆信息业务对象 veh_vehicle_info
*
* @author lilemy
* @date 2025-10-25
*/
@Data
@EqualsAndHashCode(callSuper = true)
@AutoMapper(target = VehVehicleInfo.class, reverseConvertGenerate = false)
public class VehVehicleInfoBo extends BaseEntity {
/**
* 主键ID
*/
@NotNull(message = "主键ID不能为空", groups = {EditGroup.class})
private Long id;
/**
* 项目ID
*/
@NotNull(message = "项目ID不能为空", groups = {AddGroup.class, EditGroup.class})
private Long projectId;
/**
* 车牌号
*/
@NotBlank(message = "车牌号不能为空", groups = {AddGroup.class, EditGroup.class})
private String plateNumber;
/**
* 车辆品牌
*/
@NotBlank(message = "车辆品牌不能为空", groups = {AddGroup.class, EditGroup.class})
private String vehicleBrand;
/**
* 车辆类型
*/
@NotBlank(message = "车辆类型不能为空", groups = {AddGroup.class, EditGroup.class})
private String vehicleType;
/**
* 车辆颜色
*/
@NotBlank(message = "车辆颜色不能为空", groups = {AddGroup.class, EditGroup.class})
private String vehicleColor;
/**
* 座位数
*/
@NotNull(message = "座位数不能为空", groups = {AddGroup.class, EditGroup.class})
private Integer seatCount;
/**
* 燃料类型
*/
@NotBlank(message = "燃料类型不能为空", groups = {AddGroup.class, EditGroup.class})
private String fuelType;
/**
* 车辆状态
*/
@NotBlank(message = "车辆状态不能为空", groups = {AddGroup.class, EditGroup.class})
private String vehicleStatus;
/**
* 车长(米)
*/
private BigDecimal vehicleLength;
/**
* 车宽(米)
*/
private BigDecimal vehicleWidth;
/**
* 车高(米)
*/
private BigDecimal vehicleHeight;
/**
* 轴距(米)
*/
private BigDecimal wheelBase;
/**
* 轮距(米)
*/
private BigDecimal wheelTrack;
/**
* 车辆性质
*/
@NotBlank(message = "车辆性质不能为空", groups = {AddGroup.class, EditGroup.class})
private String ownerType;
/**
* 租赁方信息
*/
private String rentalCompany;
/**
* 登记证书编号(车管所登记凭证)
*/
private String registrationCertNo;
/**
* 登记日期
*/
private LocalDate registerDate;
/**
* 购置日期
*/
private LocalDate purchaseDate;
/**
* 购置价格
*/
private BigDecimal purchasePrice;
/**
* 保险到期时间
*/
private LocalDate insuranceExpiry;
/**
* 年检到期时间
*/
private LocalDate inspectionExpiry;
/**
* 附件ID
*/
private String fileIds;
/**
* 备注
*/
private String remark;
}

View File

@ -0,0 +1,80 @@
package org.dromara.vehicle.domain.dto.vehicleapply;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* @author lilemy
* @date 2025-10-27 14:15
*/
@Data
public class VehVehicleApplyCreateReq implements Serializable {
@Serial
private static final long serialVersionUID = 1199219811382958686L;
/**
* 项目ID
*/
@NotNull(message = "项目ID不能为空")
private Long projectId;
/**
* 关联行程ID
*/
@NotNull(message = "关联行程ID不能为空")
private Long tripId;
/**
* 申请人数
*/
@NotNull(message = "申请人数不能为空")
private Integer peopleNum;
/**
* 联系电话
*/
private String passengerPhone;
/**
* 出发地
*/
private String startPlace;
/**
* 目的地
*/
@NotBlank(message = "目的地不能为空")
private String endPlace;
/**
* 出发地经度
*/
private String startLat;
/**
* 出发地纬度
*/
private String startLng;
/**
* 目的地经度
*/
@NotBlank(message = "目的地经度不能为空")
private String endLat;
/**
* 目的地纬度
*/
@NotBlank(message = "目的地纬度不能为空")
private String endLng;
/**
* 备注
*/
private String remark;
}

View File

@ -0,0 +1,52 @@
package org.dromara.vehicle.domain.dto.vehicleapply;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* @author lilemy
* @date 2025-10-27 14:48
*/
@Data
public class VehVehicleApplyQueryReq implements Serializable {
@Serial
private static final long serialVersionUID = -7148064523789231728L;
/**
* 项目ID
*/
private Long projectId;
/**
* 关联行程ID
*/
private Long tripId;
/**
* 申请人数
*/
private Integer peopleNum;
/**
* 联系电话
*/
private String passengerPhone;
/**
* 出发地
*/
private String startPlace;
/**
* 目的地
*/
private String endPlace;
/**
* 乘车状态
*/
private String status;
}

View File

@ -0,0 +1,31 @@
package org.dromara.vehicle.domain.dto.vehicleapply;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* @author lilemy
* @date 2025-10-27 15:00
*/
@Data
public class VehVehicleApplyReviewReq implements Serializable {
@Serial
private static final long serialVersionUID = -5881272503469997069L;
/**
* 主键
*/
@NotNull(message = "主键不能为空")
private Long id;
/**
* 乘车状态
*/
@NotBlank(message = "乘车状态不能为空")
private String status;
}

View File

@ -0,0 +1,79 @@
package org.dromara.vehicle.domain.dto.vehicleapply;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* @author lilemy
* @date 2025-10-27 15:30
*/
@Data
public class VehVehicleApplyUpdateReq implements Serializable {
@Serial
private static final long serialVersionUID = 7272254511495824388L;
/**
* 主键ID
*/
@NotNull(message = "主键不能为空")
private Long id;
/**
* 项目ID
*/
private Long projectId;
/**
* 关联行程ID
*/
private Long tripId;
/**
* 申请人数
*/
private Integer peopleNum;
/**
* 联系电话
*/
private String passengerPhone;
/**
* 出发地
*/
private String startPlace;
/**
* 目的地
*/
private String endPlace;
/**
* 出发地经度
*/
private String startLat;
/**
* 出发地纬度
*/
private String startLng;
/**
* 目的地经度
*/
private String endLat;
/**
* 目的地纬度
*/
private String endLng;
/**
* 备注
*/
private String remark;
}

View File

@ -0,0 +1,24 @@
package org.dromara.vehicle.domain.dto.vehicletrip;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* @author lilemy
* @date 2025-10-27 09:22
*/
@Data
public class VehVehicleTripCancelReq implements Serializable {
@Serial
private static final long serialVersionUID = 7690656986769836247L;
/**
* 主键ID
*/
@NotNull(message = "主键不能为空")
private Long id;
}

View File

@ -0,0 +1,109 @@
package org.dromara.vehicle.domain.dto.vehicletrip;
import jakarta.validation.constraints.NotBlank;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
import java.util.Date;
/**
* @author lilemy
* @date 2025-10-27 10:05
*/
@Data
public class VehVehicleTripCreateReq implements Serializable {
@Serial
private static final long serialVersionUID = 7691668678158594767L;
/**
* 项目ID
*/
private Long projectId;
/**
* 车辆ID
*/
private Long vehicleId;
/**
* 车牌号
*/
private String plateNumber;
/**
* 联系电话
*/
private String passengerPhone;
/**
* 出行事由
*/
private String tripReason;
/**
* 出发地
*/
@NotBlank(message = "出发地不能为空")
private String startPlace;
/**
* 目的地
*/
@NotBlank(message = "目的地不能为空")
private String endPlace;
/**
* 出发地经度
*/
@NotBlank(message = "出发地经度不能为空")
private String startLat;
/**
* 出发地纬度
*/
@NotBlank(message = "出发地纬度不能为空")
private String startLng;
/**
* 目的地经度
*/
@NotBlank(message = "目的地经度不能为空")
private String endLat;
/**
* 目的地纬度
*/
@NotBlank(message = "目的地纬度不能为空")
private String endLng;
/**
* 计划出发时间
*/
@NotNull(message = "计划出发时间不能为空")
private Date startTime;
/**
* 计划到达时间
*/
private Date endTime;
/**
* 申请人数
*/
@NotNull(message = "申请人数不能为空")
private Integer peopleNum;
/**
* 剩余座位数
*/
@NotNull(message = "剩余座位数不能为空")
private Integer leftSeat;
/**
* 备注
*/
private String remark;
}

View File

@ -0,0 +1,54 @@
package org.dromara.vehicle.domain.dto.vehicletrip;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
import java.util.Date;
/**
* @author lilemy
* @date 2025-10-25 19:40
*/
@Data
public class VehVehicleTripQueryReq implements Serializable {
@Serial
private static final long serialVersionUID = -7795154504461471208L;
/**
* 项目ID
*/
private Long projectId;
/**
* 目的地
*/
private String endPlace;
/**
* 目的地经度
*/
private String endLat;
/**
* 目的地纬度
*/
private String endLng;
/**
* 计划出发时间
*/
private Date startTime;
/**
* 出行人数
*/
private Integer peopleNum;
/**
* 审核状态
*/
private String reviewStatus;
}

View File

@ -0,0 +1,105 @@
package org.dromara.vehicle.domain.dto.vehicletrip;
import jakarta.validation.constraints.NotNull;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
import java.util.Date;
/**
* @author lilemy
* @date 2025-10-27 11:33
*/
@Data
public class VehVehicleTripUpdateReq implements Serializable {
@Serial
private static final long serialVersionUID = 3855392201273235078L;
/**
* 主键ID
*/
@NotNull(message = "主键不能为空")
private Long id;
/**
* 项目ID
*/
private Long projectId;
/**
* 车辆ID
*/
private Long vehicleId;
/**
* 车牌号
*/
private String plateNumber;
/**
* 联系电话
*/
private String passengerPhone;
/**
* 出行事由
*/
private String tripReason;
/**
* 出发地
*/
private String startPlace;
/**
* 目的地
*/
private String endPlace;
/**
* 出发地经度
*/
private String startLat;
/**
* 出发地纬度
*/
private String startLng;
/**
* 目的地经度
*/
private String endLat;
/**
* 目的地纬度
*/
private String endLng;
/**
* 计划出发时间
*/
private Date startTime;
/**
* 计划到达时间
*/
private Date endTime;
/**
* 申请人数
*/
private Integer peopleNum;
/**
* 剩余座位数
*/
private Integer leftSeat;
/**
* 备注
*/
private String remark;
}

View File

@ -0,0 +1,27 @@
package org.dromara.vehicle.domain.enums;
import lombok.Getter;
/**
* @author lilemy
* @date 2025-10-27 09:39
*/
@Getter
public enum VehApplyStatusEnum {
APPLYING("申请中", "1"),
CONFIRMED("已确认", "2"),
REJECTED("已拒绝", "3"),
ALREADY("已上车", "4"),
ARRIVED("已到达", "5"),
CANCELED("已取消", "6");
private final String text;
private final String value;
VehApplyStatusEnum(String text, String value) {
this.text = text;
this.value = value;
}
}

View File

@ -0,0 +1,25 @@
package org.dromara.vehicle.domain.enums;
import lombok.Getter;
/**
* @author lilemy
* @date 2025-10-27 09:32
*/
@Getter
public enum VehTripStatusEnum {
READY_DEPART("待出发","1"),
UNDERWAY("进行中","2"),
COMPLETED("已完成","3"),
CANCELED("已取消","4" );
private final String text;
private final String value;
VehTripStatusEnum(String text, String value) {
this.text = text;
this.value = value;
}
}

View File

@ -0,0 +1,25 @@
package org.dromara.vehicle.domain.enums;
import lombok.Getter;
/**
* @author lilemy
* @date 2025-10-27 11:42
*/
@Getter
public enum VehVehicleInfoStatusEnum {
AVAILABLE("可用", "1"),
IN_USE("使用中", "2"),
UNDER_MAINTENANCE("维护中", "3"),
DISABLE("停用", "4");
private final String text;
private final String value;
VehVehicleInfoStatusEnum(String text, String value) {
this.text = text;
this.value = value;
}
}

View File

@ -0,0 +1,111 @@
package org.dromara.vehicle.domain.vo;
import org.dromara.vehicle.domain.VehVehicleApply;
import com.alibaba.excel.annotation.ExcelIgnoreUnannotated;
import com.alibaba.excel.annotation.ExcelProperty;
import org.dromara.common.excel.annotation.ExcelDictFormat;
import org.dromara.common.excel.convert.ExcelDictConvert;
import io.github.linpeilie.annotations.AutoMapper;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
import java.util.Date;
/**
* 乘车申请视图对象 veh_vehicle_apply
*
* @author lilemy
* @date 2025-10-25
*/
@Data
@ExcelIgnoreUnannotated
@AutoMapper(target = VehVehicleApply.class)
public class VehVehicleApplyVo implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
/**
* 主键ID
*/
@ExcelProperty(value = "主键ID")
private Long id;
/**
* 项目ID
*/
@ExcelProperty(value = "项目ID")
private Long projectId;
/**
* 关联行程ID
*/
@ExcelProperty(value = "关联行程ID")
private Long tripId;
/**
* 申请人数
*/
@ExcelProperty(value = "申请人数")
private Integer peopleNum;
/**
* 联系电话
*/
@ExcelProperty(value = "联系电话")
private String passengerPhone;
/**
* 出发地
*/
@ExcelProperty(value = "出发地")
private String startPlace;
/**
* 目的地
*/
@ExcelProperty(value = "目的地")
private String endPlace;
/**
* 出发地经度
*/
@ExcelProperty(value = "出发地经度")
private String startLat;
/**
* 出发地纬度
*/
@ExcelProperty(value = "出发地纬度")
private String startLng;
/**
* 目的地经度
*/
@ExcelProperty(value = "目的地经度")
private String endLat;
/**
* 目的地纬度
*/
@ExcelProperty(value = "目的地纬度")
private String endLng;
/**
* 乘车状态
*/
@ExcelProperty(value = "乘车状态", converter = ExcelDictConvert.class)
@ExcelDictFormat(dictType = "veh_vehicle_apply_status")
private String status;
/**
* 备注
*/
@ExcelProperty(value = "备注")
private String remark;
}

Some files were not shown because too many files have changed in this diff Show More