Browse Source

监督端-查询统计

dev-v1.0.2
庄锐波 5 months ago
parent
commit
ab164ed5d0
  1. 105
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/controller/ComplaintStatisticsController.java
  2. 125
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/controller/web/supervision/report/StatisticsComplaintController.java
  3. 98
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/ComplaintStatistics.java
  4. 138
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/bo/ComplaintStatisticsBo.java
  5. 118
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/ComplaintStatisticsVo.java
  6. 36
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportDetailVo.java
  7. 27
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportExportVo.java
  8. 27
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportGroupVo.java
  9. 24
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportOverviewVo.java
  10. 30
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportTypeExportVo.java
  11. 27
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportTypeStatVo.java
  12. 38
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/mapper/ComplaintStatisticsMapper.java
  13. 41
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/report/IStatisticsComplaintReport.java
  14. 313
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/report/impl/StatisticsComplaintReportImpl.java
  15. 68
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/service/IComplaintStatisticsService.java
  16. 144
      zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/service/impl/ComplaintStatisticsServiceImpl.java
  17. 6
      zdxt-modules/zdxt-enforcement-code/src/main/resources/mapper/enforcementcode/ComplaintStatisticsMapper.xml
  18. 143
      zdxt-modules/zdxt-enforcement-code/src/main/resources/mapper/enforcementcode/report/ComplaintStatisticsReportMapper.xml
  19. 156
      zdxt-web-client/zdxt-admin-plus-ui/src/api/efcode/report/statistics-complaint.ts

105
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/controller/ComplaintStatisticsController.java

@ -0,0 +1,105 @@
package com.zdxt.enforcementcode.controller;
import java.util.List;
import lombok.RequiredArgsConstructor;
import jakarta.servlet.http.HttpServletResponse;
import jakarta.validation.constraints.*;
import cn.dev33.satoken.annotation.SaCheckPermission;
import org.springframework.web.bind.annotation.*;
import org.springframework.validation.annotation.Validated;
import org.dromara.common.idempotent.annotation.RepeatSubmit;
import org.dromara.common.log.annotation.Log;
import org.dromara.common.web.core.BaseController;
import org.dromara.common.mybatis.core.page.PageQuery;
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.log.enums.BusinessType;
import org.dromara.common.excel.utils.ExcelUtil;
import com.zdxt.enforcementcode.domain.vo.ComplaintStatisticsVo;
import com.zdxt.enforcementcode.domain.bo.ComplaintStatisticsBo;
import com.zdxt.enforcementcode.service.IComplaintStatisticsService;
import org.dromara.common.mybatis.core.page.TableDataInfo;
/**
* 【请填写功能名称】
*
* @author Lion Li
* @date 2026-06-13
*/
@Validated
@RequiredArgsConstructor
@RestController
@RequestMapping("/enforcementcode/statistics")
public class ComplaintStatisticsController extends BaseController {
private final IComplaintStatisticsService complaintStatisticsService;
/**
* 查询【请填写功能名称】列表
*/
@SaCheckPermission("enforcementcode:statistics:list")
@GetMapping("/list")
public TableDataInfo<ComplaintStatisticsVo> list(ComplaintStatisticsBo bo, PageQuery pageQuery) {
return complaintStatisticsService.queryPageList(bo, pageQuery);
}
/**
* 导出【请填写功能名称】列表
*/
@SaCheckPermission("enforcementcode:statistics:export")
@Log(title = "【请填写功能名称】", businessType = BusinessType.EXPORT)
@PostMapping("/export")
public void export(ComplaintStatisticsBo bo, HttpServletResponse response) {
List<ComplaintStatisticsVo> list = complaintStatisticsService.queryList(bo);
ExcelUtil.exportExcel(list, "【请填写功能名称】", ComplaintStatisticsVo.class, response);
}
/**
* 获取【请填写功能名称】详细信息
*
* @param id 主键
*/
@SaCheckPermission("enforcementcode:statistics:query")
@GetMapping("/{id}")
public R<ComplaintStatisticsVo> getInfo(@NotNull(message = "主键不能为空")
@PathVariable Long id) {
return R.ok(complaintStatisticsService.queryById(id));
}
/**
* 新增【请填写功能名称】
*/
@SaCheckPermission("enforcementcode:statistics:add")
@Log(title = "【请填写功能名称】", businessType = BusinessType.INSERT)
@RepeatSubmit()
@PostMapping()
public R<Void> add(@Validated(AddGroup.class) @RequestBody ComplaintStatisticsBo bo) {
return toAjax(complaintStatisticsService.insertByBo(bo));
}
/**
* 修改【请填写功能名称】
*/
@SaCheckPermission("enforcementcode:statistics:edit")
@Log(title = "【请填写功能名称】", businessType = BusinessType.UPDATE)
@RepeatSubmit()
@PutMapping()
public R<Void> edit(@Validated(EditGroup.class) @RequestBody ComplaintStatisticsBo bo) {
return toAjax(complaintStatisticsService.updateByBo(bo));
}
/**
* 删除【请填写功能名称】
*
* @param ids 主键串
*/
@SaCheckPermission("enforcementcode:statistics:remove")
@Log(title = "【请填写功能名称】", businessType = BusinessType.DELETE)
@DeleteMapping("/{ids}")
public R<Void> remove(@NotEmpty(message = "主键不能为空")
@PathVariable Long[] ids) {
return toAjax(complaintStatisticsService.deleteWithValidByIds(List.of(ids), true));
}
}

125
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/controller/web/supervision/report/StatisticsComplaintController.java

@ -0,0 +1,125 @@
package com.zdxt.enforcementcode.controller.web.supervision.report;
import com.zdxt.enforcementcode.domain.bo.ComplaintStatisticsBo;
import com.zdxt.enforcementcode.domain.vo.report.*;
import com.zdxt.enforcementcode.report.IStatisticsComplaintReport;
import jakarta.servlet.http.HttpServletResponse;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.dromara.common.core.domain.R;
import org.dromara.common.excel.utils.ExcelUtil;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import java.util.List;
/**
* 执法投诉情况报表
*
* @author zdxt
*/
@Slf4j
@Validated
@RequiredArgsConstructor
@RestController
@RequestMapping("/web/supervision/report/statistics-complaint")
public class StatisticsComplaintController {
private final IStatisticsComplaintReport reportService;
/** Tab1概览 */
@GetMapping("/overview")
public R<ComplaintReportOverviewVo> overview(ComplaintStatisticsBo bo) {
return R.ok(reportService.overview(bo));
}
/** Tab1主表格:按部门分组 */
@GetMapping("/groupList")
public TableDataInfo<ComplaintReportGroupVo> groupList(ComplaintStatisticsBo bo, PageQuery pageQuery) {
return reportService.groupList(bo, pageQuery);
}
/** Tab1明细列表 */
@GetMapping("/detailList")
public TableDataInfo<ComplaintReportDetailVo> detailList(ComplaintStatisticsBo bo, PageQuery pageQuery) {
return reportService.detailList(bo, pageQuery);
}
/** Tab2-投诉类型统计 */
@GetMapping("/typeStatList")
public R<List<ComplaintReportTypeStatVo>> typeStatList(ComplaintStatisticsBo bo) {
return R.ok(reportService.typeStatList(bo));
}
/** Tab2-区域统计 */
@GetMapping("/areaStatList")
public R<List<ComplaintReportTypeStatVo>> areaStatList(ComplaintStatisticsBo bo) {
return R.ok(reportService.areaStatList(bo));
}
/** Tab2-街道统计 */
@GetMapping("/streetStatList")
public R<List<ComplaintReportTypeStatVo>> streetStatList(ComplaintStatisticsBo bo) {
return R.ok(reportService.streetStatList(bo));
}
/** Tab1导出 */
@PostMapping("/exportGroupList")
public void exportGroupList(ComplaintStatisticsBo bo, HttpServletResponse response) {
try {
List<ComplaintReportExportVo> list = reportService.exportGroupList(bo);
ExcelUtil.exportExcel(list, "执法投诉统计", ComplaintReportExportVo.class, response);
} catch (Exception e) {
log.error("导出执法投诉统计Excel异常", e);
handleExportError(response, e);
}
}
/** Tab2投诉类型导出 */
@PostMapping("/exportTypeStat")
public void exportTypeStat(ComplaintStatisticsBo bo, HttpServletResponse response) {
try {
List<ComplaintReportTypeExportVo> list = reportService.exportTypeStat(bo, "type");
ExcelUtil.exportExcel(list, "投诉类型统计", ComplaintReportTypeExportVo.class, response);
} catch (Exception e) {
log.error("导出投诉类型统计Excel异常", e);
handleExportError(response, e);
}
}
/** Tab2区域导出 */
@PostMapping("/exportAreaStat")
public void exportAreaStat(ComplaintStatisticsBo bo, HttpServletResponse response) {
try {
List<ComplaintReportTypeExportVo> list = reportService.exportTypeStat(bo, "area");
ExcelUtil.exportExcel(list, "区域投诉统计", ComplaintReportTypeExportVo.class, response);
} catch (Exception e) {
log.error("导出区域投诉统计Excel异常", e);
handleExportError(response, e);
}
}
/** Tab2街道导出 */
@PostMapping("/exportStreetStat")
public void exportStreetStat(ComplaintStatisticsBo bo, HttpServletResponse response) {
try {
List<ComplaintReportTypeExportVo> list = reportService.exportTypeStat(bo, "street");
ExcelUtil.exportExcel(list, "街道投诉统计", ComplaintReportTypeExportVo.class, response);
} catch (Exception e) {
log.error("导出街道投诉统计Excel异常", e);
handleExportError(response, e);
}
}
private void handleExportError(HttpServletResponse response, Exception e) {
response.reset();
response.setContentType("application/json; charset=utf-8");
try {
response.getWriter().write("{\"code\":500,\"msg\":\"导出失败: " + e.getMessage() + "\"}");
} catch (Exception ignored) {
}
}
}

98
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/ComplaintStatistics.java

@ -0,0 +1,98 @@
package com.zdxt.enforcementcode.domain;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import com.baomidou.mybatisplus.annotation.*;
import lombok.Data;
import lombok.EqualsAndHashCode;
import java.util.Date;
import com.fasterxml.jackson.annotation.JsonFormat;
import java.io.Serial;
/**
* 【请填写功能名称】对象 complaint_statistics
*
* @author Lion Li
* @date 2026-06-13
*/
@Data
@EqualsAndHashCode(callSuper = true)
@TableName("complaint_statistics")
public class ComplaintStatistics extends BaseEntity {
@Serial
private static final long serialVersionUID = 1L;
/**
* 主键
*/
@TableId(value = "id")
private Long id;
/**
* 投诉表id
*/
private String cid;
/**
* 执法表id
*/
private String rid;
/**
* 投诉时间
*/
private Date complaintTime;
/**
* 投诉类型
*/
private Long complaintType;
/**
* 被投诉部门
*/
private String complaintDepartment;
/**
* 被投诉部门id
*/
private String complaintDepartmentId;
/**
* 企业名称
*/
private String enterpriseName;
/**
* 企业纳税识别号
*/
private String enterpriseNumber;
/**
* 投诉类型
*/
private Long enforceType;
/**
* 问题描述
*/
private String problemDescription;
/**
* 联系人
*/
private String linkman;
/**
* 联系方式
*/
private String linkmanTel;
/**
* 涉事地址
*/
private String enterpriseAddress;
}

138
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/bo/ComplaintStatisticsBo.java

@ -0,0 +1,138 @@
package com.zdxt.enforcementcode.domain.bo;
import com.zdxt.enforcementcode.domain.ComplaintStatistics;
import org.dromara.common.mybatis.core.domain.BaseEntity;
import org.dromara.common.core.validate.AddGroup;
import org.dromara.common.core.validate.EditGroup;
import io.github.linpeilie.annotations.AutoMapper;
import lombok.Data;
import lombok.EqualsAndHashCode;
import jakarta.validation.constraints.*;
import java.util.Date;
import java.util.List;
import com.fasterxml.jackson.annotation.JsonFormat;
/**
* 投诉统计业务对象 complaint_statistics
*
* @author zdxt
*/
@Data
@EqualsAndHashCode(callSuper = true)
@AutoMapper(target = ComplaintStatistics.class, reverseConvertGenerate = false)
public class ComplaintStatisticsBo extends BaseEntity {
/**
* 主键
*/
@NotNull(message = "主键不能为空", groups = { EditGroup.class })
private Long id;
/**
* 投诉表id
*/
private String cid;
/**
* 执法表id
*/
private String rid;
/**
* 投诉时间
*/
private Date complaintTime;
/**
* 投诉类型
*/
private Long complaintType;
/**
* 被投诉部门
*/
private String complaintDepartment;
/**
* 被投诉部门id
*/
private String complaintDepartmentId;
/**
* 企业名称
*/
private String enterpriseName;
/**
* 企业纳税识别号
*/
private String enterpriseNumber;
/**
* 投诉类型(字典 caseType)
*/
private Long enforceType;
/**
* 问题描述
*/
private String problemDescription;
/**
* 联系人
*/
private String linkman;
/**
* 联系方式
*/
private String linkmanTel;
/**
* 涉事地址
*/
private String enterpriseAddress;
// ===== 报表查询条件字段 =====
/**
* 年
*/
private String year;
/**
* 季度
*/
private String quarter;
/**
* 月
*/
private String month;
/**
* 自定义开始时间
*/
private String beginTime;
/**
* 自定义结束时间
*/
private String endTime;
/**
* 时段类型:year/quarter/month/day
*/
private String timeType;
/**
* Tab2类型切换:type/空/区域dict_value
*/
private String type;
/**
* 被投诉对象deptId列表(模糊搜索后填充)
*/
private List<String> complaintDepartmentIdList;
}

118
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/ComplaintStatisticsVo.java

@ -0,0 +1,118 @@
package com.zdxt.enforcementcode.domain.vo;
import java.util.Date;
import com.fasterxml.jackson.annotation.JsonFormat;
import com.zdxt.enforcementcode.domain.ComplaintStatistics;
import cn.idev.excel.annotation.ExcelIgnoreUnannotated;
import cn.idev.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;
/**
* 【请填写功能名称】视图对象 complaint_statistics
*
* @author Lion Li
* @date 2026-06-13
*/
@Data
@ExcelIgnoreUnannotated
@AutoMapper(target = ComplaintStatistics.class)
public class ComplaintStatisticsVo implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
/**
* 主键
*/
@ExcelProperty(value = "主键")
private Long id;
/**
* 投诉表id
*/
@ExcelProperty(value = "投诉表id")
private String cid;
/**
* 执法表id
*/
@ExcelProperty(value = "执法表id")
private String rid;
/**
* 投诉时间
*/
@ExcelProperty(value = "投诉时间")
private Date complaintTime;
/**
* 投诉类型
*/
@ExcelProperty(value = "投诉类型")
private Long complaintType;
/**
* 被投诉部门
*/
@ExcelProperty(value = "被投诉部门")
private String complaintDepartment;
/**
* 被投诉部门id
*/
@ExcelProperty(value = "被投诉部门id")
private String complaintDepartmentId;
/**
* 企业名称
*/
@ExcelProperty(value = "企业名称")
private String enterpriseName;
/**
* 企业纳税识别号
*/
@ExcelProperty(value = "企业纳税识别号")
private String enterpriseNumber;
/**
* 投诉类型
*/
@ExcelProperty(value = "投诉类型")
private Long enforceType;
/**
* 问题描述
*/
@ExcelProperty(value = "问题描述")
private String problemDescription;
/**
* 联系人
*/
@ExcelProperty(value = "联系人")
private String linkman;
/**
* 联系方式
*/
@ExcelProperty(value = "联系方式")
private String linkmanTel;
/**
* 涉事地址
*/
@ExcelProperty(value = "涉事地址")
private String enterpriseAddress;
}

36
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportDetailVo.java

@ -0,0 +1,36 @@
package com.zdxt.enforcementcode.domain.vo.report;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* 执法投诉情况报表 — Tab1 明细VO
*
* @author zdxt
*/
@Data
public class ComplaintReportDetailVo implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
/** 主键ID */
private Long id;
/** 投诉表ID */
private String cid;
/** 被投诉对象 */
private String complaintDepartment;
/** 投诉类型值(字典 caseType) */
private Long enforceType;
/** 投诉类型翻译 */
private String enforceTypeText;
/** 投诉时间(格式化字符串) */
private String complaintTime;
}

27
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportExportVo.java

@ -0,0 +1,27 @@
package com.zdxt.enforcementcode.domain.vo.report;
import cn.idev.excel.annotation.ExcelIgnoreUnannotated;
import cn.idev.excel.annotation.ExcelProperty;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* 执法投诉情况报表 — Tab1 导出VO
*
* @author zdxt
*/
@Data
@ExcelIgnoreUnannotated
public class ComplaintReportExportVo implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
@ExcelProperty(value = "被投诉对象")
private String complaintDepartment;
@ExcelProperty(value = "投诉数量")
private int total;
}

27
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportGroupVo.java

@ -0,0 +1,27 @@
package com.zdxt.enforcementcode.domain.vo.report;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* 执法投诉情况报表 — Tab1 分组统计VO
*
* @author zdxt
*/
@Data
public class ComplaintReportGroupVo implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
/** 被投诉对象名称 */
private String complaintDepartment;
/** 被投诉部门ID */
private String complaintDepartmentId;
/** 投诉数量 */
private int total;
}

24
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportOverviewVo.java

@ -0,0 +1,24 @@
package com.zdxt.enforcementcode.domain.vo.report;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* 执法投诉情况报表 — Tab1 概览VO
*
* @author zdxt
*/
@Data
public class ComplaintReportOverviewVo implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
/** 投诉数量 */
private int complaintCount;
/** 被投诉对象数 */
private int complaintDeptCount;
}

30
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportTypeExportVo.java

@ -0,0 +1,30 @@
package com.zdxt.enforcementcode.domain.vo.report;
import cn.idev.excel.annotation.ExcelIgnoreUnannotated;
import cn.idev.excel.annotation.ExcelProperty;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* 执法投诉情况报表 — Tab2 导出VO(投诉类型/区域/街道 通用)
*
* @author zdxt
*/
@Data
@ExcelIgnoreUnannotated
public class ComplaintReportTypeExportVo implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
@ExcelProperty(value = "名称")
private String name;
@ExcelProperty(value = "数量")
private int count;
@ExcelProperty(value = "占比")
private String percentage;
}

27
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/domain/vo/report/ComplaintReportTypeStatVo.java

@ -0,0 +1,27 @@
package com.zdxt.enforcementcode.domain.vo.report;
import lombok.Data;
import java.io.Serial;
import java.io.Serializable;
/**
* 执法投诉情况报表 — Tab2 统计VO(投诉类型/区域/街道 通用)
*
* @author zdxt
*/
@Data
public class ComplaintReportTypeStatVo implements Serializable {
@Serial
private static final long serialVersionUID = 1L;
/** 名称(类型名/区域名/街道名) */
private String name;
/** 数量 */
private int count;
/** 占比字符串(如 "12.34%") */
private String percentage;
}

38
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/mapper/ComplaintStatisticsMapper.java

@ -0,0 +1,38 @@
package com.zdxt.enforcementcode.mapper;
import com.zdxt.enforcementcode.domain.ComplaintStatistics;
import com.zdxt.enforcementcode.domain.bo.ComplaintStatisticsBo;
import com.zdxt.enforcementcode.domain.vo.ComplaintStatisticsVo;
import com.zdxt.enforcementcode.domain.vo.report.ComplaintReportDetailVo;
import com.zdxt.enforcementcode.domain.vo.report.ComplaintReportGroupVo;
import org.apache.ibatis.annotations.Param;
import org.dromara.common.mybatis.core.mapper.BaseMapperPlus;
import java.util.List;
/**
* 投诉统计 Mapper接口
*
* @author zdxt
*/
public interface ComplaintStatisticsMapper extends BaseMapperPlus<ComplaintStatistics, ComplaintStatisticsVo> {
/** Tab1:按部门分组统计 */
List<ComplaintReportGroupVo> selectComplaintGroupByDept(@Param("bo") ComplaintStatisticsBo bo);
/** Tab1:投诉明细列表 */
List<ComplaintReportDetailVo> selectComplaintDetailList(@Param("bo") ComplaintStatisticsBo bo);
/** Tab1概览:投诉总数 */
int selectComplaintCount(@Param("bo") ComplaintStatisticsBo bo);
/** Tab1概览:被投诉对象数 */
int selectComplaintDeptCount(@Param("bo") ComplaintStatisticsBo bo);
/** Tab2:查全量投诉列表(含enforce_type)用于Java层投诉类型分组 */
List<ComplaintStatistics> selectComplaintListForTypeStat(@Param("bo") ComplaintStatisticsBo bo);
/** Tab2:查全量投诉列表(含enterprise_address)用于Java层区域/街道分组 */
List<ComplaintStatistics> selectComplaintListForAreaStat(@Param("bo") ComplaintStatisticsBo bo);
}

41
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/report/IStatisticsComplaintReport.java

@ -0,0 +1,41 @@
package com.zdxt.enforcementcode.report;
import com.zdxt.enforcementcode.domain.bo.ComplaintStatisticsBo;
import com.zdxt.enforcementcode.domain.vo.report.*;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import java.util.List;
/**
* 执法投诉情况报表 Service接口
*
* @author zdxt
*/
public interface IStatisticsComplaintReport {
/** Tab1概览:投诉数量 + 被投诉对象数 */
ComplaintReportOverviewVo overview(ComplaintStatisticsBo bo);
/** Tab1主表格:按部门分组统计(含手动分页) */
TableDataInfo<ComplaintReportGroupVo> groupList(ComplaintStatisticsBo bo, PageQuery pageQuery);
/** Tab1明细列表:某部门的投诉明细(含手动分页) */
TableDataInfo<ComplaintReportDetailVo> detailList(ComplaintStatisticsBo bo, PageQuery pageQuery);
/** Tab2-投诉类型统计 */
List<ComplaintReportTypeStatVo> typeStatList(ComplaintStatisticsBo bo);
/** Tab2-区域统计 */
List<ComplaintReportTypeStatVo> areaStatList(ComplaintStatisticsBo bo);
/** Tab2-街道统计 */
List<ComplaintReportTypeStatVo> streetStatList(ComplaintStatisticsBo bo);
/** Tab1导出 */
List<ComplaintReportExportVo> exportGroupList(ComplaintStatisticsBo bo);
/** Tab2导出(投诉类型/区域/街道 通用) */
List<ComplaintReportTypeExportVo> exportTypeStat(ComplaintStatisticsBo bo, String statType);
}

313
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/report/impl/StatisticsComplaintReportImpl.java

@ -0,0 +1,313 @@
package com.zdxt.enforcementcode.report.impl;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.zdxt.enforcementcode.domain.ComplaintStatistics;
import com.zdxt.enforcementcode.domain.bo.ComplaintStatisticsBo;
import com.zdxt.enforcementcode.domain.vo.report.*;
import com.zdxt.enforcementcode.mapper.ComplaintStatisticsMapper;
import com.zdxt.enforcementcode.report.IStatisticsComplaintReport;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.dromara.common.core.domain.dto.DictDataDTO;
import org.dromara.common.core.service.DictService;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.mybatis.core.page.PageQuery;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.system.service.ISysDeptService;
import org.dromara.system.domain.vo.SysDeptVo;
import org.springframework.stereotype.Service;
import java.math.BigDecimal;
import java.math.RoundingMode;
import java.util.*;
import java.util.stream.Collectors;
/**
* 执法投诉情况报表 Service实现
* <p>
* 复刻旧系统 ComplaintStatisticsImpl 逻辑:
* - Tab1: 按 complaint_department_id 分组统计 + JOIN sys_dept 翻译名称
* - Tab2: Java层按 enforceType/enterprise_address 分组,字典翻译
* <p>
* 不使用 DataFilterUtil 进行数据过滤
*
* @author zdxt
*/
@Slf4j
@RequiredArgsConstructor
@Service
public class StatisticsComplaintReportImpl implements IStatisticsComplaintReport {
private final ComplaintStatisticsMapper complaintStatisticsMapper;
private final ISysDeptService sysDeptService;
private final DictService dictService;
@Override
public ComplaintReportOverviewVo overview(ComplaintStatisticsBo bo) {
// 处理被投诉对象模糊搜索
fillDeptIdListByName(bo);
ComplaintReportOverviewVo vo = new ComplaintReportOverviewVo();
vo.setComplaintCount(complaintStatisticsMapper.selectComplaintCount(bo));
vo.setComplaintDeptCount(complaintStatisticsMapper.selectComplaintDeptCount(bo));
return vo;
}
@Override
public TableDataInfo<ComplaintReportGroupVo> groupList(ComplaintStatisticsBo bo, PageQuery pageQuery) {
// 处理被投诉对象模糊搜索
fillDeptIdListByName(bo);
// 全量查询分组数据
List<ComplaintReportGroupVo> allList = complaintStatisticsMapper.selectComplaintGroupByDept(bo);
// 手动分页
int pageNum = pageQuery.getPageNum();
int pageSize = pageQuery.getPageSize();
int total = allList.size();
int fromIndex = Math.min((pageNum - 1) * pageSize, total);
int toIndex = Math.min(fromIndex + pageSize, total);
List<ComplaintReportGroupVo> pageRecords = allList.subList(fromIndex, toIndex);
Page<ComplaintReportGroupVo> page = new Page<>(pageNum, pageSize, total);
page.setRecords(pageRecords);
return TableDataInfo.build(page);
}
@Override
public TableDataInfo<ComplaintReportDetailVo> detailList(ComplaintStatisticsBo bo, PageQuery pageQuery) {
// 全量查询明细
List<ComplaintReportDetailVo> allList = complaintStatisticsMapper.selectComplaintDetailList(bo);
// 字典翻译 enforceType -> enforceTypeText
Map<String, String> caseTypeDict = dictService.getAllDictByDictType("caseType");
for (ComplaintReportDetailVo item : allList) {
if (item.getEnforceType() != null) {
String label = caseTypeDict.get(String.valueOf(item.getEnforceType()));
item.setEnforceTypeText(label != null ? label : String.valueOf(item.getEnforceType()));
}
}
// 手动分页
int pageNum = pageQuery.getPageNum();
int pageSize = pageQuery.getPageSize();
int total = allList.size();
int fromIndex = Math.min((pageNum - 1) * pageSize, total);
int toIndex = Math.min(fromIndex + pageSize, total);
List<ComplaintReportDetailVo> pageRecords = allList.subList(fromIndex, toIndex);
Page<ComplaintReportDetailVo> page = new Page<>(pageNum, pageSize, total);
page.setRecords(pageRecords);
return TableDataInfo.build(page);
}
@Override
public List<ComplaintReportTypeStatVo> typeStatList(ComplaintStatisticsBo bo) {
// 复刻旧系统 type() 逻辑
List<ComplaintStatistics> list = complaintStatisticsMapper.selectComplaintListForTypeStat(bo);
Map<String, String> caseTypeDict = dictService.getAllDictByDictType("caseType");
int totalCount = list.size();
// 按 enforceType 分组计数
Map<Long, Long> groupMap = list.stream()
.filter(item -> item.getEnforceType() != null)
.collect(Collectors.groupingBy(ComplaintStatistics::getEnforceType, Collectors.counting()));
List<ComplaintReportTypeStatVo> result = new ArrayList<>();
for (Map.Entry<Long, Long> entry : groupMap.entrySet()) {
ComplaintReportTypeStatVo vo = new ComplaintReportTypeStatVo();
String label = caseTypeDict.get(String.valueOf(entry.getKey()));
vo.setName(label != null ? label : String.valueOf(entry.getKey()));
vo.setCount(entry.getValue().intValue());
vo.setPercentage(calcPercentage(entry.getValue().intValue(), totalCount));
result.add(vo);
}
// 按数量降序
result.sort((a, b) -> b.getCount() - a.getCount());
return result;
}
@Override
public List<ComplaintReportTypeStatVo> areaStatList(ComplaintStatisticsBo bo) {
// 复刻旧系统 qyComplaintList() 逻辑
List<ComplaintStatistics> list = complaintStatisticsMapper.selectComplaintListForAreaStat(bo);
int totalCount = list.size();
// 获取区域字典 address_type
List<DictDataDTO> areaDictList = dictService.getDictData("address_type");
List<ComplaintReportTypeStatVo> result = new ArrayList<>();
List<ComplaintStatistics> remaining = new ArrayList<>(list);
for (DictDataDTO dict : areaDictList) {
String areaLabel = dict.getDictLabel(); // 如 "福田区"
// 构建匹配前缀:去掉"区"或"新区"后缀,再加回
String prefix = buildAreaPrefix(areaLabel);
List<ComplaintStatistics> matched = remaining.stream()
.filter(item -> item.getEnterpriseAddress() != null && item.getEnterpriseAddress().startsWith(prefix))
.collect(Collectors.toList());
ComplaintReportTypeStatVo vo = new ComplaintReportTypeStatVo();
vo.setName(areaLabel);
vo.setCount(matched.size());
vo.setPercentage(calcPercentage(matched.size(), totalCount));
result.add(vo);
remaining.removeAll(matched);
}
// 剩余归入"其他"
if (!remaining.isEmpty()) {
ComplaintReportTypeStatVo otherVo = new ComplaintReportTypeStatVo();
otherVo.setName("其他");
otherVo.setCount(remaining.size());
otherVo.setPercentage(calcPercentage(remaining.size(), totalCount));
result.add(otherVo);
}
return result;
}
@Override
public List<ComplaintReportTypeStatVo> streetStatList(ComplaintStatisticsBo bo) {
// 复刻旧系统 jdComplaintList() 逻辑
// bo.type = 选中区域的 dict_value(作为街道字典的 dict_type)
String areaDictValue = bo.getType();
if (StringUtils.isBlank(areaDictValue)) {
return new ArrayList<>();
}
// 获取区域名称(通过 address_type 字典查对应 label)
String areaLabel = dictService.getDictLabel("address_type", areaDictValue);
String areaPrefix = buildAreaPrefix(areaLabel);
// 获取全量投诉数据(含地址)
List<ComplaintStatistics> allList = complaintStatisticsMapper.selectComplaintListForAreaStat(bo);
// 先过滤出该区的记录
List<ComplaintStatistics> areaList = allList.stream()
.filter(item -> item.getEnterpriseAddress() != null && item.getEnterpriseAddress().startsWith(areaPrefix))
.collect(Collectors.toList());
int totalCount = areaList.size();
// 获取街道字典(dict_type = areaDictValue)
List<DictDataDTO> streetDictList = dictService.getDictData(areaDictValue);
List<ComplaintReportTypeStatVo> result = new ArrayList<>();
List<ComplaintStatistics> remaining = new ArrayList<>(areaList);
for (DictDataDTO dict : streetDictList) {
String streetLabel = dict.getDictLabel(); // 如 "福田街道"
String streetPrefix = areaPrefix + streetLabel;
List<ComplaintStatistics> matched = remaining.stream()
.filter(item -> item.getEnterpriseAddress() != null && item.getEnterpriseAddress().startsWith(streetPrefix))
.collect(Collectors.toList());
ComplaintReportTypeStatVo vo = new ComplaintReportTypeStatVo();
vo.setName(streetLabel);
vo.setCount(matched.size());
vo.setPercentage(calcPercentage(matched.size(), totalCount));
result.add(vo);
remaining.removeAll(matched);
}
// 剩余归入"其他"
if (!remaining.isEmpty()) {
ComplaintReportTypeStatVo otherVo = new ComplaintReportTypeStatVo();
otherVo.setName("其他");
otherVo.setCount(remaining.size());
otherVo.setPercentage(calcPercentage(remaining.size(), totalCount));
result.add(otherVo);
}
return result;
}
@Override
public List<ComplaintReportExportVo> exportGroupList(ComplaintStatisticsBo bo) {
fillDeptIdListByName(bo);
List<ComplaintReportGroupVo> allList = complaintStatisticsMapper.selectComplaintGroupByDept(bo);
return allList.stream().map(item -> {
ComplaintReportExportVo exportVo = new ComplaintReportExportVo();
exportVo.setComplaintDepartment(item.getComplaintDepartment());
exportVo.setTotal(item.getTotal());
return exportVo;
}).collect(Collectors.toList());
}
@Override
public List<ComplaintReportTypeExportVo> exportTypeStat(ComplaintStatisticsBo bo, String statType) {
List<ComplaintReportTypeStatVo> statList;
if ("type".equals(statType)) {
statList = typeStatList(bo);
} else if ("area".equals(statType)) {
statList = areaStatList(bo);
} else {
statList = streetStatList(bo);
}
return statList.stream().map(item -> {
ComplaintReportTypeExportVo exportVo = new ComplaintReportTypeExportVo();
exportVo.setName(item.getName());
exportVo.setCount(item.getCount());
exportVo.setPercentage(item.getPercentage());
return exportVo;
}).collect(Collectors.toList());
}
// ===== 私有方法 =====
/**
* 处理被投诉对象模糊搜索:通过 complaintDepartment 查询 sys_dept 获取 deptIdList
*/
private void fillDeptIdListByName(ComplaintStatisticsBo bo) {
if (StringUtils.isNotBlank(bo.getComplaintDepartment())) {
List<SysDeptVo> deptList = sysDeptService.selectDeptByDeptName(bo.getComplaintDepartment());
if (deptList != null && !deptList.isEmpty()) {
List<String> idList = deptList.stream()
.map(SysDeptVo::getDeptId)
.collect(Collectors.toList());
bo.setComplaintDepartmentIdList(idList);
} else {
// 如果模糊搜索没有匹配,设为不可能匹配的值,让结果为空
bo.setComplaintDepartmentIdList(Collections.singletonList("-1"));
}
}
}
/**
* 构建区域匹配前缀
* 复刻旧系统逻辑:enterprise_address.startsWith("深圳市" + 区名去"区"后 + "区")
* 如 "福田区" -> "深圳市福田区"
* 如 "光明区" -> "深圳市光明区"(同时尝试"新区")
*/
private String buildAreaPrefix(String areaLabel) {
if (StringUtils.isBlank(areaLabel)) {
return "深圳市";
}
// 去掉"区"或"新区"后缀,再拼接回来
String name = areaLabel;
if (name.endsWith("新区")) {
name = name.substring(0, name.length() - 2);
} else if (name.endsWith("区")) {
name = name.substring(0, name.length() - 1);
}
return "深圳市" + name + "区";
}
/**
* 计算占比
*/
private String calcPercentage(int count, int total) {
if (total == 0) {
return "0.00%";
}
BigDecimal pct = BigDecimal.valueOf(count)
.multiply(BigDecimal.valueOf(100))
.divide(BigDecimal.valueOf(total), 2, RoundingMode.HALF_UP);
return pct.toPlainString() + "%";
}
}

68
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/service/IComplaintStatisticsService.java

@ -0,0 +1,68 @@
package com.zdxt.enforcementcode.service;
import com.zdxt.enforcementcode.domain.vo.ComplaintStatisticsVo;
import com.zdxt.enforcementcode.domain.bo.ComplaintStatisticsBo;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.mybatis.core.page.PageQuery;
import java.util.Collection;
import java.util.List;
/**
* 【请填写功能名称】Service接口
*
* @author Lion Li
* @date 2026-06-13
*/
public interface IComplaintStatisticsService {
/**
* 查询【请填写功能名称】
*
* @param id 主键
* @return 【请填写功能名称】
*/
ComplaintStatisticsVo queryById(Long id);
/**
* 分页查询【请填写功能名称】列表
*
* @param bo 查询条件
* @param pageQuery 分页参数
* @return 【请填写功能名称】分页列表
*/
TableDataInfo<ComplaintStatisticsVo> queryPageList(ComplaintStatisticsBo bo, PageQuery pageQuery);
/**
* 查询符合条件的【请填写功能名称】列表
*
* @param bo 查询条件
* @return 【请填写功能名称】列表
*/
List<ComplaintStatisticsVo> queryList(ComplaintStatisticsBo bo);
/**
* 新增【请填写功能名称】
*
* @param bo 【请填写功能名称】
* @return 是否新增成功
*/
Boolean insertByBo(ComplaintStatisticsBo bo);
/**
* 修改【请填写功能名称】
*
* @param bo 【请填写功能名称】
* @return 是否修改成功
*/
Boolean updateByBo(ComplaintStatisticsBo bo);
/**
* 校验并批量删除【请填写功能名称】信息
*
* @param ids 待删除的主键集合
* @param isValid 是否进行有效性校验
* @return 是否删除成功
*/
Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid);
}

144
zdxt-modules/zdxt-enforcement-code/src/main/java/com/zdxt/enforcementcode/service/impl/ComplaintStatisticsServiceImpl.java

@ -0,0 +1,144 @@
package com.zdxt.enforcementcode.service.impl;
import org.dromara.common.core.utils.MapstructUtils;
import org.dromara.common.core.utils.StringUtils;
import org.dromara.common.mybatis.core.page.TableDataInfo;
import org.dromara.common.mybatis.core.page.PageQuery;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.stereotype.Service;
import com.zdxt.enforcementcode.domain.bo.ComplaintStatisticsBo;
import com.zdxt.enforcementcode.domain.vo.ComplaintStatisticsVo;
import com.zdxt.enforcementcode.domain.ComplaintStatistics;
import com.zdxt.enforcementcode.mapper.ComplaintStatisticsMapper;
import com.zdxt.enforcementcode.service.IComplaintStatisticsService;
import java.util.List;
import java.util.Map;
import java.util.Collection;
/**
* 【请填写功能名称】Service业务层处理
*
* @author Lion Li
* @date 2026-06-13
*/
@Slf4j
@RequiredArgsConstructor
@Service
public class ComplaintStatisticsServiceImpl implements IComplaintStatisticsService {
private final ComplaintStatisticsMapper baseMapper;
/**
* 查询【请填写功能名称】
*
* @param id 主键
* @return 【请填写功能名称】
*/
@Override
public ComplaintStatisticsVo queryById(Long id){
return baseMapper.selectVoById(id);
}
/**
* 分页查询【请填写功能名称】列表
*
* @param bo 查询条件
* @param pageQuery 分页参数
* @return 【请填写功能名称】分页列表
*/
@Override
public TableDataInfo<ComplaintStatisticsVo> queryPageList(ComplaintStatisticsBo bo, PageQuery pageQuery) {
LambdaQueryWrapper<ComplaintStatistics> lqw = buildQueryWrapper(bo);
Page<ComplaintStatisticsVo> result = baseMapper.selectVoPage(pageQuery.build(), lqw);
return TableDataInfo.build(result);
}
/**
* 查询符合条件的【请填写功能名称】列表
*
* @param bo 查询条件
* @return 【请填写功能名称】列表
*/
@Override
public List<ComplaintStatisticsVo> queryList(ComplaintStatisticsBo bo) {
LambdaQueryWrapper<ComplaintStatistics> lqw = buildQueryWrapper(bo);
return baseMapper.selectVoList(lqw);
}
private LambdaQueryWrapper<ComplaintStatistics> buildQueryWrapper(ComplaintStatisticsBo bo) {
Map<String, Object> params = bo.getParams();
LambdaQueryWrapper<ComplaintStatistics> lqw = Wrappers.lambdaQuery();
lqw.orderByAsc(ComplaintStatistics::getId);
lqw.eq(StringUtils.isNotBlank(bo.getCid()), ComplaintStatistics::getCid, bo.getCid());
lqw.eq(StringUtils.isNotBlank(bo.getRid()), ComplaintStatistics::getRid, bo.getRid());
lqw.eq(bo.getComplaintTime() != null, ComplaintStatistics::getComplaintTime, bo.getComplaintTime());
lqw.eq(bo.getComplaintType() != null, ComplaintStatistics::getComplaintType, bo.getComplaintType());
lqw.eq(StringUtils.isNotBlank(bo.getComplaintDepartment()), ComplaintStatistics::getComplaintDepartment, bo.getComplaintDepartment());
lqw.eq(StringUtils.isNotBlank(bo.getComplaintDepartmentId()), ComplaintStatistics::getComplaintDepartmentId, bo.getComplaintDepartmentId());
lqw.like(StringUtils.isNotBlank(bo.getEnterpriseName()), ComplaintStatistics::getEnterpriseName, bo.getEnterpriseName());
lqw.eq(StringUtils.isNotBlank(bo.getEnterpriseNumber()), ComplaintStatistics::getEnterpriseNumber, bo.getEnterpriseNumber());
lqw.eq(bo.getEnforceType() != null, ComplaintStatistics::getEnforceType, bo.getEnforceType());
lqw.eq(StringUtils.isNotBlank(bo.getProblemDescription()), ComplaintStatistics::getProblemDescription, bo.getProblemDescription());
lqw.eq(StringUtils.isNotBlank(bo.getLinkman()), ComplaintStatistics::getLinkman, bo.getLinkman());
lqw.eq(StringUtils.isNotBlank(bo.getLinkmanTel()), ComplaintStatistics::getLinkmanTel, bo.getLinkmanTel());
lqw.eq(StringUtils.isNotBlank(bo.getEnterpriseAddress()), ComplaintStatistics::getEnterpriseAddress, bo.getEnterpriseAddress());
return lqw;
}
/**
* 新增【请填写功能名称】
*
* @param bo 【请填写功能名称】
* @return 是否新增成功
*/
@Override
public Boolean insertByBo(ComplaintStatisticsBo bo) {
ComplaintStatistics add = MapstructUtils.convert(bo, ComplaintStatistics.class);
validEntityBeforeSave(add);
boolean flag = baseMapper.insert(add) > 0;
if (flag) {
bo.setId(add.getId());
}
return flag;
}
/**
* 修改【请填写功能名称】
*
* @param bo 【请填写功能名称】
* @return 是否修改成功
*/
@Override
public Boolean updateByBo(ComplaintStatisticsBo bo) {
ComplaintStatistics update = MapstructUtils.convert(bo, ComplaintStatistics.class);
validEntityBeforeSave(update);
return baseMapper.updateById(update) > 0;
}
/**
* 保存前的数据校验
*/
private void validEntityBeforeSave(ComplaintStatistics entity){
//TODO 做一些数据校验,如唯一约束
}
/**
* 校验并批量删除【请填写功能名称】信息
*
* @param ids 待删除的主键集合
* @param isValid 是否进行有效性校验
* @return 是否删除成功
*/
@Override
public Boolean deleteWithValidByIds(Collection<Long> ids, Boolean isValid) {
if(isValid){
//TODO 做一些业务上的校验,判断是否需要校验
}
return baseMapper.deleteByIds(ids) > 0;
}
}

6
zdxt-modules/zdxt-enforcement-code/src/main/resources/mapper/enforcementcode/ComplaintStatisticsMapper.xml

@ -0,0 +1,6 @@
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.zdxt.enforcementcode.mapper.ComplaintStatisticsMapper">
</mapper>

143
zdxt-modules/zdxt-enforcement-code/src/main/resources/mapper/enforcementcode/report/ComplaintStatisticsReportMapper.xml

@ -0,0 +1,143 @@
<?xml version="1.0" encoding="UTF-8" ?>
<!DOCTYPE mapper
PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
"http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.zdxt.enforcementcode.mapper.ComplaintStatisticsMapper">
<!-- 通用时间条件片段 -->
<sql id="reportTimeCondition">
<if test="bo.year != null and bo.year != '' and (bo.timeType == null or bo.timeType == '' or bo.timeType == 'year')">
AND YEAR(complaint_time) = #{bo.year}
</if>
<if test="bo.timeType == 'quarter' and bo.year != null and bo.year != '' and bo.quarter != null and bo.quarter != ''">
AND YEAR(complaint_time) = #{bo.year} AND QUARTER(complaint_time) = #{bo.quarter}
</if>
<if test="bo.timeType == 'month' and bo.year != null and bo.year != '' and bo.month != null and bo.month != ''">
AND YEAR(complaint_time) = #{bo.year} AND MONTH(complaint_time) = #{bo.month}
</if>
<if test="bo.timeType == 'day' and bo.beginTime != null and bo.beginTime != ''">
AND DATE_FORMAT(complaint_time,'%Y-%m-%d') &gt;= STR_TO_DATE(#{bo.beginTime},'%Y-%m-%d')
</if>
<if test="bo.timeType == 'day' and bo.endTime != null and bo.endTime != ''">
AND DATE_FORMAT(complaint_time,'%Y-%m-%d') &lt;= STR_TO_DATE(#{bo.endTime},'%Y-%m-%d')
</if>
</sql>
<!-- Tab1:分组统计(被投诉对象+数量),JOIN sys_dept翻译名称 -->
<select id="selectComplaintGroupByDept" resultType="com.zdxt.enforcementcode.domain.vo.report.ComplaintReportGroupVo">
SELECT c.complaint_department_id AS complaintDepartmentId,
d.dept_name AS complaintDepartment,
COUNT(*) AS total
FROM complaint_statistics c
LEFT JOIN sys_dept d ON c.complaint_department_id = d.dept_id
WHERE c.complaint_department_id IS NOT NULL
AND c.complaint_department IS NOT NULL
AND c.enforce_type IS NOT NULL
<if test="bo.complaintDepartmentIdList != null and bo.complaintDepartmentIdList.size() > 0">
AND c.complaint_department_id IN
<foreach collection="bo.complaintDepartmentIdList" item="deptId" open="(" separator="," close=")">
#{deptId}
</foreach>
</if>
<if test="bo.enforceType != null">
AND c.enforce_type = #{bo.enforceType}
</if>
<if test="bo.enterpriseAddress != null and bo.enterpriseAddress != ''">
AND c.enterprise_address LIKE CONCAT('%', #{bo.enterpriseAddress}, '%')
</if>
<include refid="reportTimeCondition"/>
GROUP BY c.complaint_department_id
ORDER BY total DESC
</select>
<!-- Tab1:投诉明细列表 -->
<select id="selectComplaintDetailList" resultType="com.zdxt.enforcementcode.domain.vo.report.ComplaintReportDetailVo">
SELECT c.id, c.cid, c.complaint_department AS complaintDepartment,
c.enforce_type AS enforceType,
DATE_FORMAT(c.complaint_time, '%Y-%m-%d %H:%i:%s') AS complaintTime
FROM complaint_statistics c
WHERE c.complaint_department_id IS NOT NULL
AND c.complaint_department IS NOT NULL
AND c.enforce_type IS NOT NULL
<if test="bo.complaintDepartmentId != null and bo.complaintDepartmentId != ''">
AND c.complaint_department_id = #{bo.complaintDepartmentId}
</if>
<if test="bo.enforceType != null">
AND c.enforce_type = #{bo.enforceType}
</if>
<if test="bo.enterpriseAddress != null and bo.enterpriseAddress != ''">
AND c.enterprise_address LIKE CONCAT('%', #{bo.enterpriseAddress}, '%')
</if>
<include refid="reportTimeCondition"/>
ORDER BY c.complaint_time DESC
</select>
<!-- Tab1概览:投诉总数 -->
<select id="selectComplaintCount" resultType="int">
SELECT COUNT(*) FROM complaint_statistics
WHERE complaint_department_id IS NOT NULL
AND complaint_department IS NOT NULL
AND enforce_type IS NOT NULL
<if test="bo.complaintDepartmentIdList != null and bo.complaintDepartmentIdList.size() > 0">
AND complaint_department_id IN
<foreach collection="bo.complaintDepartmentIdList" item="deptId" open="(" separator="," close=")">
#{deptId}
</foreach>
</if>
<if test="bo.enforceType != null">
AND enforce_type = #{bo.enforceType}
</if>
<if test="bo.enterpriseAddress != null and bo.enterpriseAddress != ''">
AND enterprise_address LIKE CONCAT('%', #{bo.enterpriseAddress}, '%')
</if>
<include refid="reportTimeCondition"/>
</select>
<!-- Tab1概览:被投诉对象数 -->
<select id="selectComplaintDeptCount" resultType="int">
SELECT COUNT(DISTINCT complaint_department_id) FROM complaint_statistics
WHERE complaint_department_id IS NOT NULL
AND complaint_department IS NOT NULL
AND enforce_type IS NOT NULL
<if test="bo.complaintDepartmentIdList != null and bo.complaintDepartmentIdList.size() > 0">
AND complaint_department_id IN
<foreach collection="bo.complaintDepartmentIdList" item="deptId" open="(" separator="," close=")">
#{deptId}
</foreach>
</if>
<if test="bo.enforceType != null">
AND enforce_type = #{bo.enforceType}
</if>
<if test="bo.enterpriseAddress != null and bo.enterpriseAddress != ''">
AND enterprise_address LIKE CONCAT('%', #{bo.enterpriseAddress}, '%')
</if>
<include refid="reportTimeCondition"/>
</select>
<!-- Tab2:查全量投诉列表(含enforce_type)用于Java层投诉类型分组 -->
<select id="selectComplaintListForTypeStat" resultType="com.zdxt.enforcementcode.domain.ComplaintStatistics">
SELECT id, enforce_type AS enforceType
FROM complaint_statistics
WHERE complaint_department_id IS NOT NULL
AND complaint_department IS NOT NULL
AND enforce_type IS NOT NULL
<include refid="reportTimeCondition"/>
</select>
<!-- Tab2:查全量投诉列表(含enterprise_address)用于Java层区域/街道分组 -->
<select id="selectComplaintListForAreaStat" resultType="com.zdxt.enforcementcode.domain.ComplaintStatistics">
SELECT c.id, i.enterprise_address AS enterpriseAddress
FROM complaint_statistics c
LEFT JOIN (
SELECT enterprise_number, enterprise_address
FROM enterprise_information
GROUP BY enterprise_number
) i ON c.enterprise_number = i.enterprise_number
WHERE c.complaint_department_id IS NOT NULL
AND c.complaint_department IS NOT NULL
AND c.enforce_type IS NOT NULL
<include refid="reportTimeCondition"/>
</select>
</mapper>

156
zdxt-web-client/zdxt-admin-plus-ui/src/api/efcode/report/statistics-complaint.ts

@ -0,0 +1,156 @@
import request from '@/utils/request';
import { AxiosPromise } from 'axios';
const BASE_URL = '/web/supervision/report/statistics-complaint';
/** 查询参数 */
export interface ComplaintQuery {
pageNum?: number;
pageSize?: number;
/** 被投诉对象(模糊搜索) */
complaintDepartment?: string;
/** 投诉类型(字典 caseType) */
enforceType?: number | string;
/** 涉事地址(模糊搜索) */
enterpriseAddress?: string;
/** 被投诉部门ID(明细查询用) */
complaintDepartmentId?: string;
/** 年 */
year?: string;
/** 季度 */
quarter?: string;
/** 月 */
month?: string;
/** 自定义开始时间 */
beginTime?: string;
/** 自定义结束时间 */
endTime?: string;
/** 时段类型:year/quarter/month/day */
timeType?: string;
/** Tab2类型切换:type/空/区域dict_value */
type?: string;
}
/** 概览VO */
export interface ComplaintOverviewVo {
complaintCount: number;
complaintDeptCount: number;
}
/** 分组统计VO */
export interface ComplaintGroupVo {
complaintDepartment: string;
complaintDepartmentId: string;
total: number;
}
/** 明细VO */
export interface ComplaintDetailVo {
id: number;
cid: string;
complaintDepartment: string;
enforceType: number;
enforceTypeText: string;
complaintTime: string;
}
/** Tab2 类型统计VO */
export interface ComplaintTypeStatVo {
name: string;
count: number;
percentage: string;
}
/** Tab1概览 */
export const getOverview = (params: ComplaintQuery): AxiosPromise => {
return request({
url: `${BASE_URL}/overview`,
method: 'get',
params
});
};
/** Tab1分组列表 */
export const getGroupList = (params: ComplaintQuery): AxiosPromise => {
return request({
url: `${BASE_URL}/groupList`,
method: 'get',
params
});
};
/** Tab1明细列表 */
export const getDetailList = (params: ComplaintQuery): AxiosPromise => {
return request({
url: `${BASE_URL}/detailList`,
method: 'get',
params
});
};
/** Tab2-投诉类型统计 */
export const getTypeStatList = (params: ComplaintQuery): AxiosPromise => {
return request({
url: `${BASE_URL}/typeStatList`,
method: 'get',
params
});
};
/** Tab2-区域统计 */
export const getAreaStatList = (params: ComplaintQuery): AxiosPromise => {
return request({
url: `${BASE_URL}/areaStatList`,
method: 'get',
params
});
};
/** Tab2-街道统计 */
export const getStreetStatList = (params: ComplaintQuery): AxiosPromise => {
return request({
url: `${BASE_URL}/streetStatList`,
method: 'get',
params
});
};
/** Tab1导出 */
export const exportGroupList = (data: ComplaintQuery): AxiosPromise<Blob> => {
return request({
url: `${BASE_URL}/exportGroupList`,
method: 'post',
data,
responseType: 'blob'
});
};
/** Tab2投诉类型导出 */
export const exportTypeStat = (data: ComplaintQuery): AxiosPromise<Blob> => {
return request({
url: `${BASE_URL}/exportTypeStat`,
method: 'post',
data,
responseType: 'blob'
});
};
/** Tab2区域导出 */
export const exportAreaStat = (data: ComplaintQuery): AxiosPromise<Blob> => {
return request({
url: `${BASE_URL}/exportAreaStat`,
method: 'post',
data,
responseType: 'blob'
});
};
/** Tab2街道导出 */
export const exportStreetStat = (data: ComplaintQuery): AxiosPromise<Blob> => {
return request({
url: `${BASE_URL}/exportStreetStat`,
method: 'post',
data,
responseType: 'blob'
});
};
Loading…
Cancel
Save