This commit is contained in:
2026-05-28 20:35:28 +08:00
parent 02cc8fb4c8
commit d3ee5282bd
8 changed files with 206 additions and 11 deletions
@@ -8,6 +8,7 @@ import com.budwk.app.sys.models.Sys_dict;
import com.budwk.app.sys.models.Sys_union;
import com.budwk.app.sys.services.SysDictService;
import com.budwk.app.sys.services.SysUserService;
import com.budwk.app.sys.views.View_user;
import com.budwk.app.web.commons.auth.utils.SecurityUtil;
import com.budwk.app.web.commons.base.Globals;
import com.budwk.app.zhgh.activity.basic.models.ActivityUserScope;
@@ -158,4 +159,11 @@ public class CommonController {
return Result.success(count > 0);
}
@At
@SaCheckLogin
@ApiOperation("获取登录用户数据")
public Result getLoginUserData(String groupId) {
return Result.success(dao.fetch(View_user.class, Cnd.where(View_user::getId, "=", SecurityUtil.getUserId())));
}
}
@@ -213,6 +213,7 @@ public class TourGroupController {
List<NutMap> list = listSql.getList(NutMap.class);
fillSignupMobile(list);
fillSignupFamilies(list);
Pagination<NutMap> pagination = new Pagination<>(pageForm.getPageNumber(), pageForm.getPageSize(), count, list);
return Result.success(pagination);
}
@@ -510,6 +511,50 @@ public class TourGroupController {
}
}
/**
* 查看成团报名人员时按台账ID带出家属子列表,避免前端逐行请求家属信息。
*/
private void fillSignupFamilies(List<NutMap> list) {
if (list == null || list.isEmpty()) {
return;
}
List<String> ledgerIds = new ArrayList<>();
for (NutMap item : list) {
String ledgerId = item.getString("id", "");
if (StrUtil.isNotBlank(ledgerId) && !ledgerIds.contains(ledgerId)) {
ledgerIds.add(ledgerId);
}
}
if (ledgerIds.isEmpty()) {
return;
}
Sql sql = Sqls.create("""
SELECT
ledgerId,
staffJobNo AS jobNo,
familyName AS userName,
'' AS mobile,
idCard,
relationship
FROM tour_ledger_family
WHERE delFlag = 0
AND ledgerId IN (@ledgerIds)
ORDER BY createdAt ASC
""");
sql.setParam("ledgerIds", ledgerIds.toArray(new String[0]));
sql.setCallback(Sqls.callback.maps());
tourLedgerService.dao().execute(sql);
Map<String, List<NutMap>> familyMap = new HashMap<>();
for (NutMap family : sql.getList(NutMap.class)) {
familyMap.computeIfAbsent(family.getString("ledgerId", ""), key -> new ArrayList<>()).add(family);
}
for (NutMap item : list) {
item.put("families", familyMap.getOrDefault(item.getString("id", ""), List.of()));
}
}
private Cnd buildQueryCnd(Integer year, String lineName, String lineType, String unionId) {
Cnd cnd = Cnd.NEW();
cnd.and("m.delFlag", "=", false);
@@ -1,7 +1,7 @@
<template>
<div class="search">
<slot></slot>
<div class="search-query">
<div class="search-query" v-if="isSearchButton">
<el-button type="primary" icon="el-icon-search" @click="$emit('search', null)">搜索</el-button>
</div>
</div>
@@ -9,7 +9,13 @@
<script>
module.exports = {
name: "pageFormSearch"
name: "pageFormSearch",
props: {
isSearchButton: {
type: Boolean,
default: true
}
}
}
</script>
@@ -127,6 +127,20 @@ layout("/layouts/platform.html"){
:size="tableSize"
border
@sort-change="viewPageOrder">
<el-table-column type="expand" width="50">
<template slot-scope="{row}">
<div v-if="row.families && row.families.length > 0" class="tour-family-list">
<el-table :data="row.families" :size="tableSize" border>
<el-table-column label="工号" prop="jobNo" width="130" align="center" header-align="center" show-overflow-tooltip></el-table-column>
<el-table-column label="姓名" prop="userName" width="120" align="center" header-align="center" show-overflow-tooltip></el-table-column>
<el-table-column label="亲属关系" prop="relationship" width="120" align="center" header-align="center" show-overflow-tooltip></el-table-column>
<el-table-column label="手机号" prop="mobile" width="140" align="center" header-align="center" show-overflow-tooltip></el-table-column>
<el-table-column label="身份证号" prop="idCard" min-width="190" align="center" header-align="center" show-overflow-tooltip></el-table-column>
</el-table>
</div>
<div v-else class="tour-family-empty">暂无亲属信息</div>
</template>
</el-table-column>
<el-table-column label="序号" type="index" :index="viewIndexMethod" width="80" align="center" header-align="center"></el-table-column>
<el-table-column label="工号" prop="jobNo" width="130" sortable="custom" align="center" header-align="center" show-overflow-tooltip></el-table-column>
<el-table-column label="姓名" prop="userName" width="120" sortable="custom" align="center" header-align="center" show-overflow-tooltip></el-table-column>
@@ -342,6 +356,13 @@ layout("/layouts/platform.html"){
margin-bottom: 12px;
padding-left: 10px;
}
.tour-family-list {
padding: 8px 32px;
}
.tour-family-empty {
color: #909399;
padding: 8px 32px;
}
.el-table .direct-family-row > td,
.el-table .direct-family-row > td .cell {
color: #f56c6c;
@@ -139,7 +139,7 @@ layout("/layouts/platform.html"){
</el-col>
<el-col :span="12">
<el-form-item label="联系人手机" prop="contactPhone">
<el-input v-model="formData.contactPhone" maxlength="30" placeholder="请输入联系人手机"></el-input>
<el-input v-model="formData.contactPhone" maxlength="30" placeholder="请输入联系人手机"></el-input>
</el-form-item>
</el-col>
</el-row>
@@ -221,8 +221,8 @@ layout("/layouts/platform.html"){
agencyName: [{ required: true, message: "必填", trigger: ["blur", "change"] }],
agencyCode: [{ required: true, message: "必填", trigger: ["blur", "change"] }],
contactName: [{ required: true, message: "必填", trigger: ["blur", "change"] }],
contactPhone: [{ validator: validateMobile, trigger: ["blur", "change"] }],
email: [{ validator: validateEmail, trigger: ["blur", "change"] }]
contactPhone: [{ validator: validateMobile, required: true, trigger: ["blur", "change"] }],
email: [{ validator: validateEmail, required: true, trigger: ["blur", "change"] }]
}
}
},
@@ -92,11 +92,13 @@ const COMMON_QUERY = {
this.units = data
})
} else {
this.$businessTool.listUnion(this.$store.state.user.union.id).then((data) => {
this.unions = data
})
this.$businessTool.listUnit(this.$store.state.user.union.id).then((data) => {
this.units = data
$.get("/open/common/getLoginUserData").then((result) => {
this.$businessTool.listUnion(result?.data?.unionId).then((data) => {
this.unions = data
})
this.$businessTool.listUnit(result?.data?.unionId).then((data) => {
this.units = data
})
})
}
},
@@ -130,7 +130,7 @@ layout("/layouts/platform.html"){
{ prop: "preparedBy", label: "编制类别", width: 120, sortable: true },
{ prop: "postDoctoralJoinDate", label: "进站时间", sortable: true, checked: 0 },
{ prop: "unionName", label: "所属工会", width: 120, sortable: true },
{ prop: "unitName", label: "所属单位", width: 120, sortable: true },
{ prop: "unitName", label: "所属单位", sortable: true },
{ prop: "idCardType", label: "证件类型", width: 120, sortable: true, checked: 0 },
{ prop: "idCard", label: "证件号码", width: 120, sortable: true, checked: 0 },
{ prop: "marriage", label: "婚姻状况", width: 120, sortable: true, checked: 0 },
+113
View File
@@ -5,6 +5,7 @@ import cn.afterturn.easypoi.excel.ExcelImportUtil;
import cn.afterturn.easypoi.excel.annotation.Excel;
import cn.afterturn.easypoi.excel.entity.ImportParams;
import cn.hutool.core.codec.Base64;
import cn.hutool.core.date.DateUtil;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.CharsetUtil;
import cn.hutool.core.util.StrUtil;
@@ -14,11 +15,13 @@ import cn.hutool.http.HttpUtil;
import cn.hutool.json.JSONArray;
import cn.hutool.json.JSONObject;
import cn.hutool.json.JSONUtil;
import com.budwk.app.base.constant.RoleConstant;
import com.budwk.app.base.sms.SmsService;
import com.budwk.app.base.utils.ManyAddOrRenewUtil;
import com.budwk.app.base.utils.PwdUtil;
import com.budwk.app.sys.models.*;
import com.budwk.app.sys.services.SysDictService;
import com.budwk.app.sys.services.SysRoleService;
import com.budwk.app.sys.services.SysUnitService;
import com.budwk.app.sys.services.SysUserService;
import com.budwk.app.web.commons.auth.utils.SecurityUtil;
@@ -72,6 +75,8 @@ public class JugTest {
@Inject
private SysUnitService sysUnitService;
@Inject
private SysRoleService sysRoleService;
@Inject
private Dao dao;
@Inject
private SmsService smsService;
@@ -101,5 +106,113 @@ public class JugTest {
List<String> users = list.stream().map(ClubUser::getUserId).distinct().toList();
clubUserService.clubUser2Scope(clubId, users);
}
@Test
public void importCommonRole() {
Sys_role memberRole = sysRoleService.getByCode(RoleConstant.PUBLIC);
dao.clear(Sys_user_role.class,Cnd.NEW().and(Sys_user_role::getRoleId, "=", memberRole.getId()));
List<Sys_user> sysUsers = dao.query(Sys_user.class, Cnd.NEW());
List<Sys_user_role> sysUserRoles = sysUsers.stream().map(user -> {
Sys_user_role userRole = new Sys_user_role();
userRole.setUserId(user.getId());
userRole.setRoleId(memberRole.getId());
return userRole;
}).collect(Collectors.toList());
dao.insert(sysUserRoles);
}
@Test
public void importZJIPCMemberRoster() {
File dir = new File("C:\\Users\\mayn\\Desktop\\客户\\浙江工业职业学院\\基础数据\\浙江工业职业技术学院最新会员名册");
File[] files = dir.listFiles((file, name) -> name.endsWith(".xls") || name.endsWith(".xlsx"));
if (files == null || files.length == 0) {
System.out.println("未找到会员名单 Excel 文件");
return;
}
Arrays.sort(files, Comparator.comparing(File::getName));
ImportParams importParams = new ImportParams();
importParams.setTitleRows(1);
importParams.setHeadRows(1);
List<MemberRosterImportTemp> importList = new ArrayList<>();
for (File file : files) {
List<MemberRosterImportTemp> rows = ExcelImportUtil.importExcel(file, MemberRosterImportTemp.class, importParams);
importList.addAll(rows.stream()
.filter(row -> StrUtil.isNotBlank(row.getLoginName()))
.toList());
}
List<String> loginNames = importList.stream()
.map(MemberRosterImportTemp::getLoginName)
.map(String::trim)
.distinct()
.toList();
if (Lang.isEmpty(loginNames)) {
System.out.println("Excel 中未读取到有效教工号");
return;
}
Sys_role memberRole = sysRoleService.getByCode(RoleConstant.MEMBER);
if (memberRole == null) {
System.out.println("会员角色不存在");
return;
}
List<Sys_user> users = dao.query(Sys_user.class, Cnd.where(Sys_user::getLoginname, "in", loginNames));
Map<String, Sys_user> userMap = users.stream().collect(Collectors.toMap(Sys_user::getLoginname, Function.identity(), (a, b) -> a));
List<String> missingLoginNames = loginNames.stream()
.filter(loginName -> !userMap.containsKey(loginName))
.toList();
if (Lang.isNotEmpty(missingLoginNames)) {
System.out.println("系统中未匹配到的教工号:" + missingLoginNames);
}
List<String> userIds = users.stream().map(Sys_user::getId).distinct().toList();
if (Lang.isEmpty(userIds)) {
System.out.println("没有可导入为会员的用户");
return;
}
// 模仿 /platform/member/info/batchMake/batchMake:设置会员状态和入会时间。
dao.update(Sys_user.class, Chain.make("member", true)
.add("memberTime", DateUtil.now()),
Cnd.where(Sys_user::getId, "in", userIds));
List<Sys_user_role> existingRoles = dao.query(Sys_user_role.class, Cnd.where(Sys_user_role::getUserId, "in", userIds)
.and(Sys_user_role::getRoleId, "=", memberRole.getId()));
Set<String> hasRoleUserIds = existingRoles.stream().map(Sys_user_role::getUserId).collect(Collectors.toSet());
List<Sys_user_role> roleList = userIds.stream()
.filter(userId -> !hasRoleUserIds.contains(userId))
.map(userId -> {
Sys_user_role userRole = new Sys_user_role();
userRole.setUserId(userId);
userRole.setRoleId(memberRole.getId());
return userRole;
})
.toList();
if (Lang.isNotEmpty(roleList)) {
dao.insert(roleList);
}
System.out.println("Excel 读取人数:" + importList.size());
System.out.println("有效教工号数:" + loginNames.size());
System.out.println("匹配并设置会员人数:" + userIds.size());
System.out.println("新增会员角色人数:" + roleList.size());
}
@Data
public static class MemberRosterImportTemp {
@Excel(name = "姓名")
private String userName;
@Excel(name = "部门")
private String unitName;
@Excel(name = "教工号")
private String loginName;
@Excel(name = "联系电话")
private String mobile;
}
}