diff --git a/src/main/java/io/v/nutz/diseaseaid/controller/DiseaseAidDashBoard.java b/src/main/java/io/v/nutz/diseaseaid/controller/DiseaseAidDashBoard.java index f3dc817..eb2c570 100644 --- a/src/main/java/io/v/nutz/diseaseaid/controller/DiseaseAidDashBoard.java +++ b/src/main/java/io/v/nutz/diseaseaid/controller/DiseaseAidDashBoard.java @@ -1,21 +1,31 @@ package io.v.nutz.diseaseaid.controller; +import cn.afterturn.easypoi.excel.ExcelExportUtil; +import cn.afterturn.easypoi.excel.entity.ExportParams; +import cn.afterturn.easypoi.excel.entity.params.ExcelExportEntity; import io.v.nutz.annontation.ViReturn; import io.v.nutz.base.utils.DateUtil; import io.v.nutz.diseaseaid.mode.AidFundMemberMode; import io.v.nutz.diseaseaid.service.AidFundMemberAuditRecordService; import io.v.nutz.diseaseaid.service.MedicalAidService; import io.v.nutz.member.service.MemberService; +import io.v.nutz.modules.models.PageForm; +import org.apache.poi.ss.usermodel.Workbook; import org.apache.shiro.authz.annotation.RequiresPermissions; import org.nutz.dao.Cnd; import org.nutz.dao.Sqls; import org.nutz.dao.entity.Record; import org.nutz.dao.sql.Sql; +import org.nutz.dao.util.cri.SqlExpressionGroup; import org.nutz.ioc.loader.annotation.Inject; import org.nutz.ioc.loader.annotation.IocBean; +import org.nutz.lang.Strings; import org.nutz.mvc.annotation.At; import org.nutz.mvc.annotation.Ok; +import javax.servlet.http.HttpServletResponse; +import java.io.IOException; +import java.util.ArrayList; import java.util.List; import java.util.Map; @@ -58,6 +68,7 @@ public class DiseaseAidDashBoard { SELECT un.unionname, un.unioncode, + un.id unionid, ( SELECT count( 1 ) FROM `user` WHERE unionid = un.id and aidFundMember = @code ) `value` FROM sys_union un @@ -188,5 +199,200 @@ public class DiseaseAidDashBoard { return medicalAidService.count(sql); } + /** + * 看板指标下钻明细 + */ + @At + @ViReturn + @RequiresPermissions("aid.dashboard") + public Object detailPage(PageForm pageForm, String detailType, Integer year, Integer medicalType, + Integer stateId, String unionId, String unitId, String personType, + String userState, String sex, String searchKeyword, + String startTime, String endTime) { + Sql sql = buildDetailSql(detailType, year, medicalType, stateId, unionId, unitId, + personType, userState, sex, searchKeyword, startTime, endTime); + return medicalAidService.listPage(pageForm.getPageNumber(), pageForm.getPageSize(), sql); + } + + /** + * 导出当前筛选条件下的全部下钻明细 + */ + @At + @Ok("void") + @RequiresPermissions("aid.dashboard") + public void exportDetail(HttpServletResponse response, String detailType, Integer year, Integer medicalType, + Integer stateId, String unionId, String unitId, String personType, + String userState, String sex, String searchKeyword, + String startTime, String endTime) throws IOException { + Sql sql = buildDetailSql(detailType, year, medicalType, stateId, unionId, unitId, + personType, userState, sex, searchKeyword, startTime, endTime); + List list = medicalAidService.list(sql); + List columns = new ArrayList<>(); + columns.add(new ExcelExportEntity("工号", "loginname", 18)); + columns.add(new ExcelExportEntity("姓名", "username", 16)); + columns.add(new ExcelExportEntity("性别", "sex", 10)); + columns.add(new ExcelExportEntity("人员类型", "personType", 18)); + columns.add(new ExcelExportEntity("在职状态", "userState", 16)); + columns.add(new ExcelExportEntity("所属工会", "unionname", 25)); + columns.add(new ExcelExportEntity("所属单位", "unitname", 25)); + if ("medical".equals(detailType)) { + columns.add(new ExcelExportEntity("补助类型", "typeName", 18)); + columns.add(new ExcelExportEntity("申请时间", "detailTime", 20)); + columns.add(new ExcelExportEntity("申请状态", "state_name", 18)); + columns.add(new ExcelExportEntity("补助金额", "total_grant", 18)); + } else { + columns.add(new ExcelExportEntity("加入时间", "detailTime", 20)); + } + + String fileName = "medical".equals(detailType) ? "医疗互助申请明细.xls" : "基金会员明细.xls"; + response.setContentType("application/octet-stream"); + response.setHeader("Content-Disposition", "attachment;filename=" + + new String(fileName.getBytes("UTF-8"), "ISO8859-1")); + Workbook workbook = ExcelExportUtil.exportExcel(new ExportParams(), columns, list); + workbook.write(response.getOutputStream()); + workbook.close(); + } + + /** + * 明细弹窗筛选选项 + */ + @At + @ViReturn + @RequiresPermissions("aid.dashboard") + public Object detailOptions() { + Sql sql = Sqls.create(""" + SELECT DISTINCT + s.state_id value, + s.state_name label + FROM state s + INNER JOIN medicalaid med ON med.state_id = s.state_id + ORDER BY s.state_id + """); + return Map.of("medicalStates", medicalAidService.list(sql)); + } + + private Sql buildDetailSql(String detailType, Integer year, Integer medicalType, Integer stateId, + String unionId, String unitId, String personType, String userState, + String sex, String searchKeyword, String startTime, String endTime) { + if ("medical".equals(detailType)) { + return buildMedicalDetailSql(year, medicalType, stateId, unionId, unitId, personType, + userState, sex, searchKeyword, startTime, endTime); + } + return buildMemberDetailSql(year, unionId, unitId, personType, userState, sex, + searchKeyword, startTime, endTime); + } + + private Sql buildMemberDetailSql(Integer year, String unionId, String unitId, String personType, + String userState, String sex, String searchKeyword, + String startTime, String endTime) { + Sql sql = Sqls.create(""" + SELECT + u.id, + u.loginname, + u.username, + u.sex, + u.personType, + u.userState, + u.unionid, + u.unionname, + u.unitid, + u.unitname, + u.aidFundMemberJoinTime detailTime + FROM user u + $condition + """); + Cnd cnd = Cnd.where("u.aidFundMember", "=", AidFundMemberMode.NORMAL.getCode()); + if (year != null) { + cnd.and("YEAR(u.aidFundMemberJoinTime)", "=", year); + } + addUserCondition(cnd, "u", unionId, unitId, personType, userState, sex, + searchKeyword, startTime, endTime, "aidFundMemberJoinTime"); + sql.setCondition(cnd.asc("u.unioncode").asc("u.loginname")); + return sql; + } + + private Sql buildMedicalDetailSql(Integer year, Integer medicalType, Integer stateId, + String unionId, String unitId, String personType, + String userState, String sex, String searchKeyword, + String startTime, String endTime) { + Sql sql = Sqls.create(""" + SELECT + med.id, + u.loginname, + med.user_name username, + u.sex, + u.personType, + u.userState, + u.unionid, + un.unionname, + u.unitid, + unit.name unitname, + med.type, + CASE med.type + WHEN 1 THEN '医疗补助' + WHEN 2 THEN '重疾补助' + WHEN 3 THEN '特殊门诊补助' + ELSE '其他' + END typeName, + med.apply_time detailTime, + med.state_id, + s.state_name, + med.total_grant + FROM medicalaid med + LEFT JOIN user u ON med.user_id = u.id + LEFT JOIN sys_union un ON u.unionid = un.id + LEFT JOIN sys_unit unit ON u.unitid = unit.id + LEFT JOIN state s ON med.state_id = s.state_id + $condition + """); + Cnd cnd = Cnd.NEW(); + if (year != null) { + cnd.and("med.year", "=", year); + } + if (medicalType != null) { + cnd.and("med.type", "=", medicalType); + } + if (stateId != null) { + cnd.and("med.state_id", "=", stateId); + } + addUserCondition(cnd, "u", unionId, unitId, personType, userState, sex, + searchKeyword, startTime, endTime, "med.apply_time"); + sql.setCondition(cnd.desc("med.apply_time")); + return sql; + } + + private void addUserCondition(Cnd cnd, String alias, String unionId, String unitId, + String personType, String userState, String sex, + String searchKeyword, String startTime, String endTime, + String timeField) { + if (Strings.isNotBlank(unionId)) { + cnd.and(alias + ".unionid", "=", unionId); + } + if (Strings.isNotBlank(unitId)) { + cnd.and(alias + ".unitid", "=", unitId); + } + if (Strings.isNotBlank(personType)) { + cnd.and(alias + ".personType", "=", personType); + } + if (Strings.isNotBlank(userState)) { + cnd.and(alias + ".userState", "=", userState); + } + if (Strings.isNotBlank(sex)) { + cnd.and(alias + ".sex", "=", sex); + } + if (Strings.isNotBlank(startTime)) { + cnd.and(timeField, ">=", startTime); + } + if (Strings.isNotBlank(endTime)) { + cnd.and(timeField, "<=", endTime + " 23:59:59"); + } + if (Strings.isNotBlank(searchKeyword)) { + SqlExpressionGroup group = new SqlExpressionGroup(); + group.orLike(alias + ".username", searchKeyword); + group.orLike(alias + ".loginname", searchKeyword); + cnd.and(group); + } + } + } diff --git a/src/main/java/io/v/nutz/member/controller/inquire/MemberDataBoardController.java b/src/main/java/io/v/nutz/member/controller/inquire/MemberDataBoardController.java index 05af8af..05825b2 100644 --- a/src/main/java/io/v/nutz/member/controller/inquire/MemberDataBoardController.java +++ b/src/main/java/io/v/nutz/member/controller/inquire/MemberDataBoardController.java @@ -1,18 +1,28 @@ package io.v.nutz.member.controller.inquire; +import cn.afterturn.easypoi.excel.ExcelExportUtil; +import cn.afterturn.easypoi.excel.entity.ExportParams; +import cn.afterturn.easypoi.excel.entity.params.ExcelExportEntity; import io.v.nutz.annontation.ViReturn; import io.v.nutz.base.utils.DateUtil; import io.v.nutz.member.service.MemberService; +import io.v.nutz.modules.models.PageForm; +import org.apache.poi.ss.usermodel.Workbook; import org.apache.shiro.authz.annotation.RequiresAuthentication; import org.apache.shiro.authz.annotation.RequiresPermissions; +import org.nutz.dao.Cnd; import org.nutz.dao.Sqls; import org.nutz.dao.entity.Record; import org.nutz.dao.sql.Sql; +import org.nutz.dao.util.cri.SqlExpressionGroup; import org.nutz.ioc.loader.annotation.Inject; import org.nutz.ioc.loader.annotation.IocBean; +import org.nutz.lang.Strings; import org.nutz.mvc.annotation.At; import org.nutz.mvc.annotation.Ok; +import javax.servlet.http.HttpServletResponse; +import java.io.IOException; import java.util.ArrayList; import java.util.List; import java.util.Map; @@ -47,7 +57,7 @@ public class MemberDataBoardController { @ViReturn public Object memberNumber() { int memberNum = memberService.count(Sqls.create("select count(1) from member")); - int lastYearMemberNum = memberService.count(Sqls.create("select * from member_his where year = year(now()) -1 ")); + int lastYearMemberNum = memberService.count(Sqls.create("select * from member_his where year = year(now()) -1 and member = 1 ")); return Map.of("memberNum", memberNum, "lastYearMemberNum", lastYearMemberNum); } @@ -60,7 +70,7 @@ public class MemberDataBoardController { List result = new ArrayList<>(); Integer year = DateUtil.getYear(); for (int i = year - 5; i < year; i++) { - int count = memberService.count(Sqls.create("select * from member_his where year = @year ").setParam("year", year)); + int count = memberService.count(Sqls.create("select * from member_his where year = @year and member = 1 ").setParam("year", i)); result.add(Map.of("label", i, "value", count)); } result.add(Map.of("label", year, "value", memberService.count(Sqls.create("select count(1) from member")))); @@ -104,6 +114,7 @@ public class MemberDataBoardController { SELECT un.unionname, un.unioncode, + un.id unionid, ( SELECT count( 1 ) FROM member WHERE unionid = un.id ) `value` FROM sys_union un @@ -166,5 +177,122 @@ public class MemberDataBoardController { return memberService.list(sql); } + /** + * 看板指标下钻明细 + */ + @At + @ViReturn + @RequiresPermissions("member.inquire.board") + public Object detailPage(PageForm pageForm, Integer year, String unionId, String unitId, + String personType, String userState, String sex, String searchKeyword, + String startTime, String endTime) { + return memberService.list(pageForm, buildDetailSql(year, unionId, unitId, personType, + userState, sex, searchKeyword, startTime, endTime)); + } + + /** + * 导出当前筛选条件下的全部下钻明细 + */ + @At + @Ok("void") + @RequiresPermissions("member.inquire.board") + public void exportDetail(HttpServletResponse response, Integer year, String unionId, String unitId, + String personType, String userState, String sex, String searchKeyword, + String startTime, String endTime) throws IOException { + List list = memberService.list(buildDetailSql(year, unionId, unitId, personType, + userState, sex, searchKeyword, startTime, endTime)); + List columns = new ArrayList<>(); + columns.add(new ExcelExportEntity("工号", "loginname", 18)); + columns.add(new ExcelExportEntity("姓名", "username", 16)); + columns.add(new ExcelExportEntity("性别", "sex", 10)); + columns.add(new ExcelExportEntity("人员类型", "personType", 18)); + columns.add(new ExcelExportEntity("在职状态", "userState", 16)); + columns.add(new ExcelExportEntity("所属工会", "unionname", 25)); + columns.add(new ExcelExportEntity("所属单位", "unitname", 25)); + columns.add(new ExcelExportEntity("入会时间", "detailTime", 18)); + + response.setContentType("application/octet-stream"); + response.setHeader("Content-Disposition", "attachment;filename=" + + new String("会员看板明细.xls".getBytes("UTF-8"), "ISO8859-1")); + Workbook workbook = ExcelExportUtil.exportExcel(new ExportParams(), columns, list); + workbook.write(response.getOutputStream()); + workbook.close(); + } + + /** + * 明细弹窗附加选项,会员看板暂无业务状态选项 + */ + @At + @ViReturn + @RequiresPermissions("member.inquire.board") + public Object detailOptions() { + return Map.of("medicalStates", List.of()); + } + + private Sql buildDetailSql(Integer year, String unionId, String unitId, String personType, + String userState, String sex, String searchKeyword, + String startTime, String endTime) { + int currentYear = DateUtil.getYear(); + boolean history = year != null && year != currentYear; + String timeField = "h.memberJoinTime"; + Sql sql = Sqls.create(""" + SELECT + m.id, + m.loginname, + m.username, + m.sex, + m.personType, + m.userState, + m.unionid, + m.unionname, + m.unitid, + m.unitname, + $detailTime detailTime + FROM $table m + $detailJoin + $condition + """) + .setVar("table", history ? "member_his" : "`user`") + .setVar("detailTime", timeField) + .setVar("detailJoin", history + ? "LEFT JOIN member_history h ON h.id = m.id AND h.year = m.year" + : "LEFT JOIN sys_user h ON h.id = m.id"); + Cnd cnd = Cnd.NEW(); + cnd.and("m.member", "=", 1); + if (history) { + cnd.and("m.year", "=", year); + } + if (Strings.isNotBlank(unionId)) { + cnd.and("m.unionid", "=", unionId); + } + if (Strings.isNotBlank(unitId)) { + cnd.and("m.unitid", "=", unitId); + } + if (Strings.isNotBlank(personType)) { + cnd.and("m.personType", "=", personType); + } + if (Strings.isNotBlank(userState)) { + cnd.and("m.userState", "=", userState); + } + if (Strings.isNotBlank(sex)) { + cnd.and("m.sex", "=", sex); + } + if (Strings.isNotBlank(startTime)) { + cnd.and(timeField, ">=", startTime); + } + if (Strings.isNotBlank(endTime)) { + cnd.and(timeField, "<=", endTime + " 23:59:59"); + } + if (Strings.isNotBlank(searchKeyword)) { + SqlExpressionGroup group = new SqlExpressionGroup(); + group.orLike("m.username", searchKeyword); + group.orLike("m.loginname", searchKeyword); + cnd.and(group); + } + cnd.asc("m.unioncode").asc("m.loginname"); + sql.setCondition(cnd); + return sql; + } + } diff --git a/src/main/resources/static/components/dashboard/DataBoardDetail.vue b/src/main/resources/static/components/dashboard/DataBoardDetail.vue new file mode 100644 index 0000000..cbfd03f --- /dev/null +++ b/src/main/resources/static/components/dashboard/DataBoardDetail.vue @@ -0,0 +1,246 @@ + + + + + diff --git a/src/main/resources/views/platform/diseaseaid/DashBoard.html b/src/main/resources/views/platform/diseaseaid/DashBoard.html index 5aebff1..f6523e0 100644 --- a/src/main/resources/views/platform/diseaseaid/DashBoard.html +++ b/src/main/resources/views/platform/diseaseaid/DashBoard.html @@ -74,13 +74,23 @@ layout("/layouts/platform.html"){ color: white !important; background-color: #314659 !important; } + .dashboard-drill { + cursor: pointer; + } + + .dashboard-drill:hover .card-value-num, + .dashboard-drill:hover .card-label { + color: #409EFF; + }