Ver Fonte

设备管理费、流量卡费财务对账

李进 há 1 ano atrás
pai
commit
4fe1c1d00d

+ 150 - 4
device-api-service/src/main/java/com/xy/service/DeviceChargingHistoryServiceImpl.java

@@ -1,19 +1,42 @@
 package com.xy.service;
 
+import com.alibaba.excel.annotation.ExcelProperty;
+import com.alibaba.excel.annotation.write.style.ColumnWidth;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.core.metadata.IPage;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.github.yitter.idgen.YitIdHelper;
 import com.xy.collections.list.JArrayList;
+import com.xy.collections.list.JList;
+import com.xy.config.DeviceThreadPoolConfig;
+import com.xy.config.FileConfig;
 import com.xy.dto.DeviceChargingHistoryDto;
 import com.xy.dto.OrderMercManageDto;
+import com.xy.dto.be.MercDto;
 import com.xy.entity.DeviceChargingHistory;
 import com.xy.mapper.DeviceChargingHistoryMapper;
+import com.xy.service.be.MercService;
+import com.xy.util.ExcelUtils;
 import com.xy.utils.*;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
 import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.SneakyThrows;
+import lombok.experimental.Accessors;
 import org.springframework.stereotype.Service;
+import org.springframework.web.bind.annotation.PostMapping;
+import org.springframework.web.bind.annotation.RequestBody;
 
+import javax.servlet.http.HttpServletResponse;
+import java.io.File;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.time.YearMonth;
+import java.time.temporal.ChronoUnit;
+import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.List;
 
 import static com.xy.utils.Beans.copy;
@@ -34,6 +57,12 @@ public class DeviceChargingHistoryServiceImpl extends ServiceImpl<DeviceCharging
 
     private OrderMercManageService orderMercManageService;
 
+    private MercService mercService;
+
+    private HttpServletResponse response;
+
+    private FileConfig fileConfig;
+
     @Override
     @ApiOperation("分页查询")
     public R<PageBean<DeviceChargingHistoryDto.Vo>> page(DeviceChargingHistoryDto.Page page) {
@@ -44,11 +73,128 @@ public class DeviceChargingHistoryServiceImpl extends ServiceImpl<DeviceCharging
         PageBean<DeviceChargingHistoryDto.Vo> pageBean = toPageBean(DeviceChargingHistoryDto.Vo.class, iPage);
         List<DeviceChargingHistoryDto.Vo> records = pageBean.getRecords();
         if (Emptys.check(records)) {
-            copy(records).target(
-                    () -> orderMercManageService.list(new OrderMercManageDto.SelectList().setId(new JArrayList<>(records).getProperty(DeviceChargingHistoryDto.Vo::getOrderId))).getData()
-                    , DeviceChargingHistoryDto.Vo::getOrderId, DeviceChargingHistoryDto.Vo::getFiles, OrderMercManageDto.Vo::getId, OrderMercManageDto.Vo::getFiles
-            ).builder();
+            copy(records)
+                    .target(() -> orderMercManageService.list(new OrderMercManageDto.SelectList().setId(new JArrayList<>(records).getProperty(DeviceChargingHistoryDto.Vo::getOrderId))).getData()
+                            , DeviceChargingHistoryDto.Vo::getOrderId, DeviceChargingHistoryDto.Vo::getFiles, OrderMercManageDto.Vo::getId, OrderMercManageDto.Vo::getFiles
+                    )
+                    .target(() -> mercService.list(new MercDto.SelectList().setMercIds(new JArrayList<>(records).getProperty(DeviceChargingHistoryDto.Vo::getMercId).comparing())).getData(),
+                            DeviceChargingHistoryDto.Vo::getMercId, DeviceChargingHistoryDto.Vo::getMercName, MercDto.Vo::getId, MercDto.Vo::getName)
+                    .builder();
         }
         return R.ok(pageBean);
     }
+
+    @ApiOperation("月统计")
+    @PostMapping("moonCount")
+    public R<List<DeviceChargingHistoryDto.MoonCountVo>> moonCount(@RequestBody DeviceChargingHistoryDto.MoonCount moonCount) {
+        JList<DeviceChargingHistoryDto.MoonCountVo> moonCountVos = new JArrayList<>();
+        //查询数据
+        List<String> attrNames = Arrays.asList(
+                LambdaUtils.getUnderlineCaseName(DeviceChargingHistory::getMercId),
+                "DATE_FORMAT(" + LambdaUtils.getUnderlineCaseName(DeviceChargingHistory::getCreateTime) + ", '%Y-%m')",
+                LambdaUtils.getUnderlineCaseName(DeviceChargingHistory::getMercId)
+        );
+        List<String> selectNames = Arrays.asList(
+                attrNames.get(0),
+                attrNames.get(1) + " " + LambdaUtils.getProperty(DeviceChargingHistory::getNote),
+                String.format("count(*) %s", LambdaUtils.getProperty(DeviceChargingHistory::getChargingSize)),
+                String.format("sum(%s) %s", LambdaUtils.getUnderlineCaseName(DeviceChargingHistory::getChargingMoney), LambdaUtils.getProperty(DeviceChargingHistory::getChargingMoney))
+        );
+        List<String> dateDifference = getDateDifference(moonCount.getBeginDate(), moonCount.getEndDate());
+        ThreadPoolUtils.Execute execute = ThreadPoolUtils.excPoll(DeviceThreadPoolConfig.DEVICE_COMMON_POLL, dateDifference.size());
+        dateDifference.forEach(date -> execute.execute(() -> {
+            QueryWrapper<DeviceChargingHistory> queryWrapper = new QueryWrapper<DeviceChargingHistory>()
+                    .select(selectNames.get(0), selectNames.get(1), selectNames.get(2), selectNames.get(3))
+                    .in(Emptys.check(moonCount.getMercIds()), attrNames.get(0), moonCount.getMercIds())
+                    .eq(attrNames.get(1), date)
+                    .groupBy(attrNames.get(0), attrNames.get(1));
+            List<DeviceChargingHistory> deviceChargingHistories = list(queryWrapper);
+            deviceChargingHistories.forEach(deviceChargingHistory -> {
+                DeviceChargingHistoryDto.MoonCountVo moonCountVo = new DeviceChargingHistoryDto.MoonCountVo()
+                        .setDate(deviceChargingHistory.getNote())
+                        .setMercId(deviceChargingHistory.getMercId())
+                        .setDeviceSize(deviceChargingHistory.getChargingSize())
+                        .setChargingMoney(deviceChargingHistory.getChargingMoney());
+                moonCountVos.add(moonCountVo);
+            });
+        }));
+        execute.end();
+        //翻译商户名称
+        Beans.copy(moonCountVos).target(() -> mercService.list(new MercDto.SelectList().setMercIds(moonCountVos.getProperty(DeviceChargingHistoryDto.MoonCountVo::getMercId).comparing())).getData(),
+                DeviceChargingHistoryDto.MoonCountVo::getMercId, DeviceChargingHistoryDto.MoonCountVo::getMercName, MercDto.Vo::getId, MercDto.Vo::getName)
+                .builder();
+        return R.ok(moonCountVos.asc(DeviceChargingHistoryDto.MoonCountVo::getDate));
+    }
+
+    @SneakyThrows
+    @ApiOperation("月统计导出")
+    @PostMapping("moonCountDownload")
+    public void moonCountDownload(@RequestBody DeviceChargingHistoryDto.MoonCount moonCount) {
+        //生成excel
+        String name = YitIdHelper.nextId() + ".xlsx";
+        String path = fileConfig.getPath() + File.separator + name;
+        ExcelUtils.SheetAndData<MoonCountData> sheetAndData = ExcelUtils.create(path, MoonCountData.class);
+        sheetAndData.sheet("设备管理费月统计数据", () -> {
+            List<DeviceChargingHistoryDto.MoonCountVo> data = moonCount(moonCount).getData();
+            if (!Emptys.check(data)) {
+                return null;
+            }
+            return Beans.copy(MoonCountData.class, data);
+        });
+        //下载文件
+        InputStream inputStream = IoUtils.inputStream(path).get();
+        response.setHeader("Content-Disposition", "attachment; filename=" + "设备管理费月统计数据.xlsx");
+        response.setContentType("application/xlsx");
+        byte[] buffer = new byte[1024];
+        int bytesRead;
+        OutputStream outputStream = response.getOutputStream();
+        while ((bytesRead = inputStream.read(buffer)) != -1) {
+            outputStream.write(buffer, 0, bytesRead);
+        }
+        inputStream.close();
+        outputStream.close();
+        //删除文件
+        new File(path).delete();
+    }
+
+    public List<String> getDateDifference(String date1, String date2) {
+        List<String> dateDifference = new ArrayList<>();
+        // 解析日期字符串
+        YearMonth yearMonth1 = YearMonth.parse(date1);
+        YearMonth yearMonth2 = YearMonth.parse(date2);
+        // 计算日期差异
+        long monthsDiff = ChronoUnit.MONTHS.between(yearMonth1, yearMonth2);
+        // 将差异的每个月添加到集合中
+        YearMonth temp = yearMonth1;
+        for (int i = 0; i <= monthsDiff; i++) {
+            dateDifference.add(temp.toString());
+            temp = temp.plusMonths(1);
+        }
+        return dateDifference;
+    }
+
+    @Data
+    @Accessors(chain = true)
+    public static class MoonCountData {
+
+        @ColumnWidth(25)
+        @ExcelProperty(value = "统计时间 yyyy-MM")
+        private String date;
+
+        @ColumnWidth(25)
+        @ExcelProperty(value = "商户id")
+        private Long mercId;
+
+        @ColumnWidth(25)
+        @ExcelProperty(value = "商户名称")
+        private String mercName;
+
+        @ColumnWidth(25)
+        @ExcelProperty(value = "设备数")
+        private Integer deviceSize;
+
+        @ColumnWidth(25)
+        @ExcelProperty(value = "续费金额")
+        private Integer chargingMoney;
+    }
 }

+ 130 - 8
device-api-service/src/main/java/com/xy/service/DeviceSimChargeServiceImpl.java

@@ -1,24 +1,39 @@
 package com.xy.service;
 
+import com.alibaba.excel.annotation.ExcelProperty;
+import com.alibaba.excel.annotation.write.style.ColumnWidth;
 import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
 import com.baomidou.mybatisplus.core.metadata.IPage;
 import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
+import com.github.yitter.idgen.YitIdHelper;
 import com.xy.collections.list.JArrayList;
+import com.xy.collections.list.JList;
+import com.xy.config.DeviceThreadPoolConfig;
+import com.xy.config.FileConfig;
 import com.xy.dto.DeviceSimChargeDto;
 import com.xy.dto.OrderMercManageDto;
+import com.xy.dto.be.MercDto;
 import com.xy.entity.DeviceSimCharge;
 import com.xy.mapper.DeviceSimChargeMapper;
-import com.xy.utils.Emptys;
-import com.xy.utils.MybatisPlusQuery;
-import com.xy.utils.PageBean;
-import com.xy.utils.R;
+import com.xy.service.be.MercService;
+import com.xy.util.ExcelUtils;
+import com.xy.utils.*;
 import io.swagger.annotations.Api;
 import io.swagger.annotations.ApiOperation;
 import lombok.AllArgsConstructor;
+import lombok.Data;
+import lombok.SneakyThrows;
+import lombok.experimental.Accessors;
 import org.springframework.stereotype.Service;
 import org.springframework.web.bind.annotation.PostMapping;
 import org.springframework.web.bind.annotation.RequestBody;
 
+import javax.servlet.http.HttpServletResponse;
+import java.io.File;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.util.Arrays;
 import java.util.List;
 
 import static com.xy.utils.Beans.copy;
@@ -41,6 +56,14 @@ public class DeviceSimChargeServiceImpl extends ServiceImpl<DeviceSimChargeMappe
 
     private OrderMercManageService orderMercManageService;
 
+    private MercService mercService;
+
+    private DeviceChargingHistoryServiceImpl deviceChargingHistoryService;
+
+    private HttpServletResponse response;
+
+    private FileConfig fileConfig;
+
     @PostMapping("page")
     @ApiOperation("分页查询")
     public R<PageBean<DeviceSimChargeDto.Vo>> page(@RequestBody DeviceSimChargeDto.Page page) {
@@ -52,12 +75,111 @@ public class DeviceSimChargeServiceImpl extends ServiceImpl<DeviceSimChargeMappe
         PageBean<DeviceSimChargeDto.Vo> voPageBean = toPageBean(DeviceSimChargeDto.Vo.class, iPage);
         List<DeviceSimChargeDto.Vo> records = voPageBean.getRecords();
         if (Emptys.check(records)) {
-            copy(records).target(
-                    () -> orderMercManageService.list(new OrderMercManageDto.SelectList().setId(new JArrayList<>(records).getProperty(DeviceSimChargeDto.Vo::getOrderId))).getData()
-                    , DeviceSimChargeDto.Vo::getOrderId, DeviceSimChargeDto.Vo::getFiles, OrderMercManageDto.Vo::getId, OrderMercManageDto.Vo::getFiles
-            ).builder();
+            copy(records)
+                    .target(() -> orderMercManageService.list(new OrderMercManageDto.SelectList().setId(new JArrayList<>(records).getProperty(DeviceSimChargeDto.Vo::getOrderId))).getData()
+                            , DeviceSimChargeDto.Vo::getOrderId, DeviceSimChargeDto.Vo::getFiles, OrderMercManageDto.Vo::getId, OrderMercManageDto.Vo::getFiles
+                    ).target(() -> mercService.list(new MercDto.SelectList().setMercIds(new JArrayList<>(records).getProperty(DeviceSimChargeDto.Vo::getMercId).comparing())).getData()
+                    , DeviceSimChargeDto.Vo::getMercId, DeviceSimChargeDto.Vo::getMercName, MercDto.Vo::getId, MercDto.Vo::getName)
+                    .builder();
         }
         return R.ok(voPageBean);
     }
 
+    @ApiOperation("月统计")
+    @PostMapping("moonCount")
+    public R<List<DeviceSimChargeDto.MoonCountVo>> moonCount(@RequestBody DeviceSimChargeDto.MoonCount moonCount) {
+        JList<DeviceSimChargeDto.MoonCountVo> moonCountVos = new JArrayList<>();
+        //查询数据
+        List<String> attrNames = Arrays.asList(
+                LambdaUtils.getUnderlineCaseName(DeviceSimCharge::getMercId),
+                "DATE_FORMAT(" + LambdaUtils.getUnderlineCaseName(DeviceSimCharge::getCreateTime) + ", '%Y-%m')",
+                LambdaUtils.getUnderlineCaseName(DeviceSimCharge::getMercId)
+        );
+        List<String> selectNames = Arrays.asList(
+                attrNames.get(0),
+                attrNames.get(1) + " " + LambdaUtils.getProperty(DeviceSimCharge::getNote),
+                String.format("count(*) %s", LambdaUtils.getProperty(DeviceSimCharge::getSize)),
+                String.format("sum(%s) %s", LambdaUtils.getUnderlineCaseName(DeviceSimCharge::getMoney), LambdaUtils.getProperty(DeviceSimCharge::getMoney))
+        );
+        List<String> dateDifference = deviceChargingHistoryService.getDateDifference(moonCount.getBeginDate(), moonCount.getEndDate());
+        ThreadPoolUtils.Execute execute = ThreadPoolUtils.excPoll(DeviceThreadPoolConfig.DEVICE_COMMON_POLL, dateDifference.size());
+        dateDifference.forEach(date -> execute.execute(() -> {
+            QueryWrapper<DeviceSimCharge> queryWrapper = new QueryWrapper<DeviceSimCharge>()
+                    .select(selectNames.get(0), selectNames.get(1), selectNames.get(2), selectNames.get(3))
+                    .in(Emptys.check(moonCount.getMercIds()), attrNames.get(0), moonCount.getMercIds())
+                    .eq(attrNames.get(1), date)
+                    .groupBy(attrNames.get(0), attrNames.get(1));
+            List<DeviceSimCharge> deviceSimCharges = list(queryWrapper);
+            deviceSimCharges.forEach(deviceSimCharge -> {
+                DeviceSimChargeDto.MoonCountVo moonCountVo = new DeviceSimChargeDto.MoonCountVo()
+                        .setDate(deviceSimCharge.getNote())
+                        .setMercId(deviceSimCharge.getMercId())
+                        .setSimSize(deviceSimCharge.getSize())
+                        .setMoney(deviceSimCharge.getMoney());
+                moonCountVos.add(moonCountVo);
+            });
+        }));
+        execute.end();
+        //翻译商户名称
+        Beans.copy(moonCountVos).target(() -> mercService.list(new MercDto.SelectList().setMercIds(moonCountVos.getProperty(DeviceSimChargeDto.MoonCountVo::getMercId).comparing())).getData(),
+                DeviceSimChargeDto.MoonCountVo::getMercId, DeviceSimChargeDto.MoonCountVo::getMercName, MercDto.Vo::getId, MercDto.Vo::getName)
+                .builder();
+        return R.ok(moonCountVos.asc(DeviceSimChargeDto.MoonCountVo::getDate));
+    }
+
+    @SneakyThrows
+    @ApiOperation("月统计导出")
+    @PostMapping("moonCountDownload")
+    public void moonCountDownload(@RequestBody DeviceSimChargeDto.MoonCount moonCount) {
+        //生成excel
+        String name = YitIdHelper.nextId() + ".xlsx";
+        String path = fileConfig.getPath() + File.separator + name;
+        ExcelUtils.SheetAndData<MoonCountData> sheetAndData = ExcelUtils.create(path, MoonCountData.class);
+        sheetAndData.sheet("设备流量卡月统计数据", () -> {
+            List<DeviceSimChargeDto.MoonCountVo> data = moonCount(moonCount).getData();
+            if (!Emptys.check(data)) {
+                return null;
+            }
+            return Beans.copy(MoonCountData.class, data);
+        });
+        //下载文件
+        InputStream inputStream = IoUtils.inputStream(path).get();
+        response.setHeader("Content-Disposition", "attachment; filename=" + "设备管理费月统计数据.xlsx");
+        response.setContentType("application/xlsx");
+        byte[] buffer = new byte[1024];
+        int bytesRead;
+        OutputStream outputStream = response.getOutputStream();
+        while ((bytesRead = inputStream.read(buffer)) != -1) {
+            outputStream.write(buffer, 0, bytesRead);
+        }
+        inputStream.close();
+        outputStream.close();
+        //删除文件
+        new File(path).delete();
+    }
+
+    @Data
+    @Accessors(chain = true)
+    public static class MoonCountData {
+
+        @ColumnWidth(25)
+        @ExcelProperty(value = "统计时间 yyyy-MM")
+        private String date;
+
+        @ColumnWidth(25)
+        @ExcelProperty(value = "商户id")
+        private Long mercId;
+
+        @ColumnWidth(25)
+        @ExcelProperty(value = "商户名称")
+        private String mercName;
+
+        @ColumnWidth(25)
+        @ExcelProperty(value = "卡数")
+        private Integer simSize;
+
+        @ColumnWidth(25)
+        @ExcelProperty(value = "续费金额")
+        private Integer money;
+    }
 }

+ 39 - 0
device-api/src/main/java/com/xy/dto/DeviceChargingHistoryDto.java

@@ -6,7 +6,9 @@ import io.swagger.annotations.ApiModelProperty;
 import lombok.Data;
 import lombok.experimental.Accessors;
 
+import java.time.LocalDate;
 import java.time.LocalDateTime;
+import java.util.List;
 
 /**
  * <p>
@@ -59,6 +61,9 @@ public class DeviceChargingHistoryDto {
 
         @ApiModelProperty(value = "附件")
         private String files;
+
+        @ApiModelProperty(value = "商户名称")
+        private String mercName;
     }
 
     @Data
@@ -70,4 +75,38 @@ public class DeviceChargingHistoryDto {
 
     }
 
+    @Data
+    @Accessors(chain = true)
+    public static class MoonCount {
+
+        @ApiModelProperty(value = "商户id")
+        private List<Long> mercIds;
+
+        @ApiModelProperty(value = "统计时间-起 yyyy-MM")
+        private String beginDate;
+
+        @ApiModelProperty(value = "统计时间-始 yyyy-MM")
+        private String endDate;
+    }
+
+    @Data
+    @Accessors(chain = true)
+    public static class MoonCountVo {
+
+        @ApiModelProperty(value = "统计时间 yyyy-MM")
+        private String date;
+
+        @ApiModelProperty(value = "商户id")
+        private Long mercId;
+
+        @ApiModelProperty(value = "商户名称")
+        private String mercName;
+
+        @ApiModelProperty(value = "设备数")
+        private Integer deviceSize;
+
+        @ApiModelProperty(value = "续费金额")
+        private Integer chargingMoney;
+    }
+
 }

+ 38 - 0
device-api/src/main/java/com/xy/dto/DeviceSimChargeDto.java

@@ -7,6 +7,7 @@ import lombok.Data;
 import lombok.experimental.Accessors;
 
 import java.time.LocalDateTime;
+import java.util.List;
 
 /**
  * <p>
@@ -67,6 +68,43 @@ public class DeviceSimChargeDto {
 
         @ApiModelProperty(value = "附件")
         private String files;
+
+        @ApiModelProperty(value = "商户名称")
+        private String mercName;
+    }
+
+    @Data
+    @Accessors(chain = true)
+    public static class MoonCount {
+
+        @ApiModelProperty(value = "商户id")
+        private List<Long> mercIds;
+
+        @ApiModelProperty(value = "统计时间-起 yyyy-MM")
+        private String beginDate;
+
+        @ApiModelProperty(value = "统计时间-始 yyyy-MM")
+        private String endDate;
+    }
+
+    @Data
+    @Accessors(chain = true)
+    public static class MoonCountVo {
+
+        @ApiModelProperty(value = "统计时间 yyyy-MM")
+        private String date;
+
+        @ApiModelProperty(value = "商户id")
+        private Long mercId;
+
+        @ApiModelProperty(value = "商户名称")
+        private String mercName;
+
+        @ApiModelProperty(value = "卡数")
+        private Integer simSize;
+
+        @ApiModelProperty(value = "续费金额")
+        private Integer money;
     }
 
 }