diff --git a/src/main/java/com/budwk/app/sys/controller/SysDataUserQueryController.java b/src/main/java/com/budwk/app/sys/controller/SysDataUserQueryController.java new file mode 100644 index 0000000..221304f --- /dev/null +++ b/src/main/java/com/budwk/app/sys/controller/SysDataUserQueryController.java @@ -0,0 +1,32 @@ +package com.budwk.app.sys.controller; + +import cn.dev33.satoken.annotation.SaCheckPermission; +import com.budwk.app.base.result.Result; +import com.budwk.app.sys.services.SysDataUserPullService; +import org.nutz.ioc.loader.annotation.Inject; +import org.nutz.ioc.loader.annotation.IocBean; +import org.nutz.mvc.annotation.At; +import org.nutz.mvc.annotation.Ok; +import org.nutz.mvc.annotation.Param; + +@IocBean +@At("/platform/sys/data/user/query") +@Ok("json:full") +public class SysDataUserQueryController { + + @Inject + private SysDataUserPullService sysUserPullService; + + @At("") + @Ok("beetl:/platform/sys/data/user/query.html") + @SaCheckPermission("sys.data.user.query") + public void index() { + } + + @At + @SaCheckPermission("sys.data.user.query") + public Result queryData(@Param("zgh") String zgh, @Param("pageNumber") int pageNumber, + @Param("pageSize") int pageSize) { + return Result.success(sysUserPullService.queryUsers(zgh, pageNumber, pageSize)); + } +} diff --git a/src/main/java/com/budwk/app/sys/services/SysDataUserPullService.java b/src/main/java/com/budwk/app/sys/services/SysDataUserPullService.java index d12dec1..56d5d0c 100644 --- a/src/main/java/com/budwk/app/sys/services/SysDataUserPullService.java +++ b/src/main/java/com/budwk/app/sys/services/SysDataUserPullService.java @@ -15,6 +15,8 @@ public interface SysDataUserPullService extends BaseService { */ Date pull(); + NutMap queryUsers(String zgh, int pageNumber, int pageSize); + /** * 拉取人员博士后的信息 */ diff --git a/src/main/java/com/budwk/app/sys/services/impl/SysDataUserPullServiceImpl.java b/src/main/java/com/budwk/app/sys/services/impl/SysDataUserPullServiceImpl.java index 94a5be8..56a278e 100644 --- a/src/main/java/com/budwk/app/sys/services/impl/SysDataUserPullServiceImpl.java +++ b/src/main/java/com/budwk/app/sys/services/impl/SysDataUserPullServiceImpl.java @@ -334,12 +334,39 @@ public class SysDataUserPullServiceImpl extends BaseServiceImpl return url; } + @Override + public NutMap queryUsers(String zgh, int pageNumber, int pageSize) { + if (pageNumber < 1 || pageSize < 1 || pageSize > 200) { + throw new BaseException("分页参数不合法"); + } + if (!dataCenterProperties.isTokenEnabled()) { + JSONObject response = DataCenterUtil.queryPage(getDmpUrl(DMP_TEACHER_KEY), zgh, pageNumber, pageSize); + JSONObject pageInfo = response.getJSONObject("pageInfo"); + JSONArray data = response.getJSONArray("dataSet"); + if (pageInfo == null || pageInfo.getLong("total") == null || data == null) { + throw new BaseException("数据中心接口未返回有效的分页数据"); + } + return NutMap.NEW().addv("list", data).addv("totalCount", pageInfo.getLong("total")); + } + String accessToken = getDmpAccessToken(); + List records = new ArrayList<>(); + records.addAll(pullDmpUsers(getDmpUrl(DMP_TEACHER_KEY), accessToken, "在岗教职工", StrUtil.trim(zgh))); + records.addAll(pullDmpUsers(getDmpUrl(DMP_DISPATCH_KEY), accessToken, "在岗劳务派遣", StrUtil.trim(zgh))); + int from = (int) Math.min((long) (pageNumber - 1) * pageSize, records.size()); + return NutMap.NEW().addv("list", records.subList(from, Math.min(from + pageSize, records.size()))) + .addv("totalCount", records.size()); + } + /** * 分页拉取单个人员接口数据。 * 入参 url 为人员接口地址,accessToken 为信息中心令牌,sourceName 用于日志区分接口来源。 * 返回值为该接口所有分页合并后的原始人员 JSON 列表。 */ private List pullDmpUsers(String url, String accessToken, String sourceName) { + return pullDmpUsers(url, accessToken, sourceName, null); + } + + private List pullDmpUsers(String url, String accessToken, String sourceName, String zgh) { List rawDataList = new ArrayList<>(); int page = 1; int maxPage = 1; @@ -349,11 +376,14 @@ public class SysDataUserPullServiceImpl extends BaseServiceImpl // 信息中心接口单页最多返回1000条,按page循环拉完当前接口全部数据。 HttpRequest httpRequest = HttpUtil.createPost(url); httpRequest.header(Header.CONTENT_TYPE, "application/json"); - httpRequest.body(JSONUtil.toJsonStr(Map.of( - "access_token", accessToken, - "per_page", String.valueOf(DMP_PAGE_SIZE), - "page", String.valueOf(page) - ))); + Map body = new HashMap<>(); + body.put("access_token", accessToken); + body.put("per_page", String.valueOf(DMP_PAGE_SIZE)); + body.put("page", String.valueOf(page)); + if (StrUtil.isNotBlank(zgh)) { + body.put("zgh", zgh); + } + httpRequest.body(JSONUtil.toJsonStr(body)); log.info("请求{}人员数据,第{}页: {}", sourceName, page, httpRequest); String resBody = httpRequest.execute().body(); diff --git a/src/main/java/com/budwk/app/sys/utils/DataCenterUtil.java b/src/main/java/com/budwk/app/sys/utils/DataCenterUtil.java index 92ba469..62d8a3c 100644 --- a/src/main/java/com/budwk/app/sys/utils/DataCenterUtil.java +++ b/src/main/java/com/budwk/app/sys/utils/DataCenterUtil.java @@ -14,6 +14,7 @@ import com.budwk.app.sys.models.Sys_unit; import java.lang.reflect.Field; import java.util.ArrayList; +import java.util.HashMap; import java.util.List; import java.util.Map; @@ -40,7 +41,11 @@ public class DataCenterUtil { } public static List pullData(String url) { - JSONObject firstResponse = requestData(url, Map.of("", "")); + return pullData(url, Map.of("", "")); + } + + public static List pullData(String url, Map params) { + JSONObject firstResponse = requestData(url, params); JSONObject pageInfo = firstResponse.getJSONObject("pageInfo"); Integer pages = pageInfo == null ? null : pageInfo.getInt("pages"); if (pages == null || pages < 0) { @@ -48,7 +53,9 @@ public class DataCenterUtil { } List records = new ArrayList<>(); for (int page = 1; page <= pages; page++) { - JSONObject response = requestData(url, Map.of("pageNum", page)); + Map body = new HashMap<>(params); + body.put("pageNum", page); + JSONObject response = requestData(url, body); JSONArray data = response.getJSONArray("dataSet"); if (data == null) { throw new BaseException("数据中心接口第{}页缺少 dataSet", page); @@ -58,6 +65,16 @@ public class DataCenterUtil { return records; } + public static JSONObject queryPage(String url, String zgh, int pageNumber, int pageSize) { + Map body = new HashMap<>(); + body.put("pageNum", pageNumber); + body.put("pageSize", pageSize); + if (StrUtil.isNotBlank(zgh)) { + body.put("zgh", zgh.trim()); + } + return requestData(url, body); + } + private static JSONObject requestData(String url, Map body) { try (HttpResponse response = HttpUtil.createPost(url) .body(JSONUtil.toJsonStr(body)).execute()) { diff --git a/src/main/resources/db/sys/sys_data_user_query_menu.sql b/src/main/resources/db/sys/sys_data_user_query_menu.sql new file mode 100644 index 0000000..af205a8 --- /dev/null +++ b/src/main/resources/db/sys/sys_data_user_query_menu.sql @@ -0,0 +1,28 @@ +-- 在人员数据拉取菜单同级新增实时查询入口,沿用现有菜单的角色授权。 +INSERT INTO sys_menu ( + id, parentId, path, name, type, href, target, icon, showit, disabled, + permission, location, hasChildren, platform, moduleId, + createdBy, createdAt, updatedBy, updatedAt, delFlag +) +SELECT 'bc6cf4034e9449bfa6e81c7d26509129', source.parentId, + CONCAT(LEFT(source.path, CHAR_LENGTH(source.path) - 4), + LPAD(COALESCE((SELECT MAX(CAST(RIGHT(sibling.path, 4) AS UNSIGNED)) + FROM sys_menu sibling WHERE sibling.parentId = source.parentId), 0) + 1, 4, '0')), + '数据中心人员查询', 'menu', '/platform/sys/data/user/query', source.target, + source.icon, 1, 0, 'sys.data.user.query', source.location + 1, 0, + source.platform, source.moduleId, '', UNIX_TIMESTAMP(NOW()) * 1000, + '', UNIX_TIMESTAMP(NOW()) * 1000, 0 +FROM sys_menu source +WHERE source.permission = 'sys.data.user.pull' + AND NOT EXISTS (SELECT 1 FROM sys_menu WHERE permission = 'sys.data.user.query') +LIMIT 1; + +INSERT INTO sys_role_menu (roleId, menuId) +SELECT DISTINCT relation.roleId, target.id +FROM sys_role_menu relation +JOIN sys_menu source ON source.id = relation.menuId AND source.permission = 'sys.data.user.pull' +JOIN sys_menu target ON target.permission = 'sys.data.user.query' +WHERE NOT EXISTS ( + SELECT 1 FROM sys_role_menu existing + WHERE existing.roleId = relation.roleId AND existing.menuId = target.id +); diff --git a/src/main/resources/static/assets/staffbenefit/therapyRecuperation/component.js b/src/main/resources/static/assets/staffbenefit/therapyRecuperation/component.js index 3318468..617e55a 100644 --- a/src/main/resources/static/assets/staffbenefit/therapyRecuperation/component.js +++ b/src/main/resources/static/assets/staffbenefit/therapyRecuperation/component.js @@ -1,9 +1,9 @@ Vue.component('vi-title', { props: ['title'], template: ` -
-
-
+
+
+
{{ title }}
@@ -79,7 +79,7 @@ Vue.component('table-tool', { this.getColumns() }, template: ` - +
diff --git a/src/main/resources/static/assets/staffbenefit/therapyRecuperation/css/desktop.css b/src/main/resources/static/assets/staffbenefit/therapyRecuperation/css/desktop.css new file mode 100644 index 0000000..2ed99e1 --- /dev/null +++ b/src/main/resources/static/assets/staffbenefit/therapyRecuperation/css/desktop.css @@ -0,0 +1,189 @@ +.therapy-desktop { + font-family: "Helvetica Neue", "Microsoft YaHei", Arial, sans-serif; + font-size: 14px; + color: #303133; +} + +.therapy-desktop #app { + height: auto; + min-height: 100%; + overflow: visible; + background: transparent; +} + +.therapy-desktop #app .el-card__header { + padding: 16px 20px; + color: #303133; + font-size: 16px; + font-weight: 600; + line-height: 24px; +} + +.therapy-desktop #app .el-form-item__label { + color: #606266; + font-weight: 400; +} + +.therapy-desktop #app .search { + display: grid; + grid-template-columns: repeat(3, minmax(0, 1fr)); + gap: 16px 24px; + margin: 0; +} + +.therapy-desktop #app .search .search-item { + width: auto; + min-width: 0; + margin: 0; + padding: 0; + overflow: visible; +} + +.therapy-desktop #app .search .search-item-label { + flex: 0 0 90px; + width: 90px; + min-width: 0; + margin-right: 12px; + color: #606266; + text-align: right; + line-height: 20px; + overflow: visible; +} + +.therapy-desktop #app .search .search-item-option { + flex: 1; + width: 0; + min-width: 0; + overflow: visible; +} + +.therapy-desktop #app .search-item-option > .el-input, +.therapy-desktop #app .search-item-option > .el-select, +.therapy-desktop #app .search-item-option > .el-date-editor { + width: 100%; + max-width: 100%; +} + +.therapy-desktop #app .search-item-option > .el-radio-group { + display: flex; + flex-wrap: wrap; + gap: 4px 0; +} + +.therapy-desktop #app .search .search-query { + display: flex; + align-items: center; + gap: 10px; + width: auto; + margin: 0; + padding-left: 102px; + overflow: visible; +} + +.therapy-desktop #app .query-row { + height: auto; + min-height: 56px; + padding: 12px 0; +} + +.therapy-desktop #app .query-row > .query-row-title:empty { + display: none; +} + +.therapy-desktop #app .query-row .el-col { + min-width: 0; + overflow: visible; +} + +.therapy-desktop #app .query-row-content { + flex: 1; +} + +.therapy-desktop #app .query-row-content > .el-row { + display: flex; + flex-wrap: wrap; + row-gap: 12px; +} + +.therapy-desktop #app .query-row-content > .el-row > .el-col { + display: flex; + align-items: center; + gap: 12px; + padding-right: 24px; +} + +.therapy-desktop #app .query-row-content > .el-row > .el-col > span:first-child { + flex: 0 0 90px; + color: #606266; + text-align: right; +} + +.therapy-desktop #app .query-row-content > .el-row > .el-col > .el-input, +.therapy-desktop #app .query-row-content > .el-row > .el-col > .el-select { + flex: 1; + width: 0 !important; + min-width: 0; +} + +.therapy-desktop .therapy-table-tool { + flex-wrap: wrap; + gap: 12px; +} + +.therapy-desktop .therapy-table-tool > div { + min-width: 0; + max-width: 100%; + flex-wrap: wrap; + gap: 10px; +} + +.therapy-desktop .therapy-title { + display: flex; + align-items: center; + min-width: 0; + margin-bottom: 16px; + color: #303133 !important; + font-size: 16px; + font-weight: 600 !important; + line-height: 24px; + overflow-wrap: anywhere; +} + +.therapy-desktop .therapy-title .therapy-title-marker { + flex: 0 0 3px; + height: 16px !important; +} + +.therapy-desktop .therapy-title .therapy-title-text { + margin-left: 10px !important; + font-size: 16px !important; + letter-spacing: normal !important; +} + +.therapy-desktop #app .chart-title, +.therapy-desktop #app .col-title { + color: #303133; + font-size: 16px; + font-weight: 600; +} + +@media (max-width: 1199px) { + .therapy-desktop #app .search { + grid-template-columns: repeat(2, minmax(0, 1fr)); + } +} + +@media (max-width: 767px) { + .therapy-desktop #app .search { + grid-template-columns: minmax(0, 1fr); + } + + .therapy-desktop #app .query-row-content > .el-row > .el-col { + width: 100%; + padding-right: 0; + } + + .therapy-desktop .therapy-table-tool > div { + width: 100%; + } +} diff --git a/src/main/resources/static/components/staffbenefit/therapyRecuperation/BaseManageInfo.vue b/src/main/resources/static/components/staffbenefit/therapyRecuperation/BaseManageInfo.vue index 3c14af0..eadfce3 100644 --- a/src/main/resources/static/components/staffbenefit/therapyRecuperation/BaseManageInfo.vue +++ b/src/main/resources/static/components/staffbenefit/therapyRecuperation/BaseManageInfo.vue @@ -1,6 +1,6 @@