|
@@ -0,0 +1,885 @@
|
|
|
+package com.management.platform.controller;
|
|
|
+
|
|
|
+
|
|
|
+import com.alibaba.fastjson.JSONArray;
|
|
|
+import com.alibaba.fastjson.JSONObject;
|
|
|
+import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
|
|
+import com.github.pagehelper.util.StringUtil;
|
|
|
+import com.management.platform.entity.*;
|
|
|
+import com.management.platform.entity.vo.SysRichFunction;
|
|
|
+import com.management.platform.entity.vo.WorktimeItem;
|
|
|
+import com.management.platform.mapper.*;
|
|
|
+import com.management.platform.service.ReportService;
|
|
|
+import com.management.platform.service.UserSalaryService;
|
|
|
+import com.management.platform.service.UserService;
|
|
|
+import com.management.platform.util.HttpRespMsg;
|
|
|
+import com.management.platform.util.ListUtil;
|
|
|
+import com.management.platform.util.WorkDayCalculateUtils;
|
|
|
+import org.apache.log4j.helpers.DateTimeDateFormat;
|
|
|
+import org.springframework.beans.factory.annotation.Autowired;
|
|
|
+import org.springframework.web.bind.annotation.RequestMapping;
|
|
|
+import org.springframework.web.bind.annotation.RequestParam;
|
|
|
+import org.springframework.web.bind.annotation.RestController;
|
|
|
+import org.springframework.web.multipart.MultipartFile;
|
|
|
+
|
|
|
+import javax.annotation.Resource;
|
|
|
+import javax.servlet.http.HttpServletRequest;
|
|
|
+import java.math.BigDecimal;
|
|
|
+import java.text.ParseException;
|
|
|
+import java.text.SimpleDateFormat;
|
|
|
+import java.time.DayOfWeek;
|
|
|
+import java.time.LocalDate;
|
|
|
+import java.time.LocalDateTime;
|
|
|
+import java.time.format.DateTimeFormatter;
|
|
|
+import java.util.*;
|
|
|
+import java.util.stream.Collectors;
|
|
|
+
|
|
|
+/**
|
|
|
+ * <p>
|
|
|
+ * 前端控制器
|
|
|
+ * </p>
|
|
|
+ *
|
|
|
+ * @author 屈跃庭
|
|
|
+ * @since 2019-12-31
|
|
|
+ */
|
|
|
+@RestController
|
|
|
+@RequestMapping("/report")
|
|
|
+public class ReportController {
|
|
|
+ @Autowired
|
|
|
+ private ReportService reportService;
|
|
|
+ @Resource
|
|
|
+ private HttpServletRequest request;
|
|
|
+ @Resource
|
|
|
+ private AuditWorkflowTimeSettingMapper auditWorkflowTimeSettingMapper;
|
|
|
+ @Resource
|
|
|
+ private UserService userService;
|
|
|
+ @Resource
|
|
|
+ private DepartmentMapper departmentMapper;
|
|
|
+ @Resource
|
|
|
+ private UserSalaryService userSalaryService;
|
|
|
+ @Resource
|
|
|
+ private TimeTypeMapper timeTypeMapper;
|
|
|
+ @Resource
|
|
|
+ private ProjectMapper projectMapper;
|
|
|
+ @Resource
|
|
|
+ private SysFunctionMapper sysFunctionMapper;
|
|
|
+
|
|
|
+
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 根据时间 按照人分类 获取报告信息
|
|
|
+ * date 日期 格式yyyy-mm-dd
|
|
|
+ */
|
|
|
+ @RequestMapping("/getReportFillStatus")
|
|
|
+ public HttpRespMsg getReportFillStatus(String startDate, String endDate, String userId) {
|
|
|
+ return reportService.getReportFillStatus(startDate, endDate, userId, request);
|
|
|
+ }
|
|
|
+
|
|
|
+ @RequestMapping("/getReportList")
|
|
|
+ public HttpRespMsg getReportList(@RequestParam String date, @RequestParam(required = false) Integer deptId, @RequestParam(required = false) String userId) {
|
|
|
+ return reportService.getReportList(date, deptId, userId, request);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 导出报告
|
|
|
+ * date 日期 格式yyyy-mm-dd
|
|
|
+ */
|
|
|
+ @RequestMapping("/exportReport")
|
|
|
+ public HttpRespMsg exportReport(String startDate, String endDate, Integer projectId) {
|
|
|
+ return reportService.exportReport(startDate, endDate, projectId, request);
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 根据时间 获取本人报告信息 以及工时
|
|
|
+ * date 日期 格式yyyy-mm-dd
|
|
|
+ */
|
|
|
+ @RequestMapping("/getReport")
|
|
|
+ public HttpRespMsg getReport(@RequestParam String date) {
|
|
|
+ return reportService.getReport(date, request);
|
|
|
+ }
|
|
|
+
|
|
|
+ private void fillReportProgress(Report report, String professionProgress) {
|
|
|
+ if (!StringUtil.isEmpty(professionProgress)) {
|
|
|
+ professionProgress = professionProgress.replaceAll("@",",");
|
|
|
+ System.out.println("JSON=="+professionProgress);
|
|
|
+ JSONArray array = JSONArray.parseArray(professionProgress);
|
|
|
+ List<ReportProfessionProgress> list = new ArrayList<ReportProfessionProgress>();
|
|
|
+ for(int i=0;i<array.size();i++) {
|
|
|
+ JSONObject jsonObject = array.getJSONObject(i);
|
|
|
+ ReportProfessionProgress item = new ReportProfessionProgress();
|
|
|
+ item.setProfessionId(jsonObject.getInteger("professionId"));
|
|
|
+ item.setProgress(jsonObject.getInteger("progress"));
|
|
|
+ item.setProjectId(report.getProjectId());
|
|
|
+ list.add(item);
|
|
|
+ }
|
|
|
+ report.setProfessionProgressList(list);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 新增或编辑报告
|
|
|
+ * id 报告id 数组
|
|
|
+ * projectId 报告相关项目id 数组
|
|
|
+ * workingTime 工作时间 数组
|
|
|
+ * content 工作内容 数组
|
|
|
+ * createDate 报告日期 数组
|
|
|
+ * draft 草稿
|
|
|
+ */
|
|
|
+ @RequestMapping("/editReport")
|
|
|
+ public HttpRespMsg editReport(Integer[] id, Integer[] projectId,
|
|
|
+ Integer[] subProjectId,
|
|
|
+ Double[] workingTime,
|
|
|
+ String[] content,
|
|
|
+ Integer[] timeType,
|
|
|
+ String[] startTime,
|
|
|
+ String[] endTime,
|
|
|
+ Integer[] reportTimeType,
|
|
|
+ String[] createDate,
|
|
|
+ Integer[] taskId,
|
|
|
+ Integer[] isOvertime,
|
|
|
+ Integer[] progress,
|
|
|
+ String[] targetUids,
|
|
|
+ String[] professionProgress,
|
|
|
+ String[] stage,
|
|
|
+ String[] pics,
|
|
|
+ Integer[] multiWorktime,
|
|
|
+ Integer[] degreeId,
|
|
|
+ @RequestParam(required = false, defaultValue = "0") Integer draft,
|
|
|
+ Integer[] groupId,//任务分组id
|
|
|
+ Double[] customData,//自定义的数值
|
|
|
+ String[] projectAuditorId
|
|
|
+ ) {
|
|
|
+ List<Report> reportList = new ArrayList<>();
|
|
|
+ String token = request.getHeader("Token");
|
|
|
+ List<String> targetUidList = null;
|
|
|
+ List<User> targetUserList = null;
|
|
|
+ if (projectId == null) {
|
|
|
+ HttpRespMsg msg = new HttpRespMsg();
|
|
|
+ msg.setError("项目不能为空");
|
|
|
+ return msg;
|
|
|
+ }
|
|
|
+ if (subProjectId == null) {
|
|
|
+ System.out.println("!!===!!有空的子项目");
|
|
|
+ subProjectId = new Integer[projectId.length];
|
|
|
+ for(int i=0;i<subProjectId.length; i++) {
|
|
|
+ subProjectId[i] = 0;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ //初始化,防止老版本无此字段奔溃报错
|
|
|
+ if (multiWorktime == null) {
|
|
|
+ multiWorktime = new Integer[projectId.length];
|
|
|
+ for(int i=0;i<multiWorktime.length; i++) {
|
|
|
+ multiWorktime[i] = 0;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ if (degreeId == null) {
|
|
|
+ degreeId = new Integer[projectId.length];
|
|
|
+ for(int i=0;i<degreeId.length; i++) {
|
|
|
+ degreeId[i] = -1;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ if (groupId == null) {
|
|
|
+ groupId = new Integer[projectId.length];
|
|
|
+ for(int i=0;i<groupId.length; i++) {
|
|
|
+ groupId[i] = 0;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ if (customData == null) {
|
|
|
+ customData = new Double[projectId.length];
|
|
|
+ for(int i=0;i<customData.length; i++) {
|
|
|
+ customData[i] = 0.0;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ if (projectAuditorId == null) {
|
|
|
+ projectAuditorId = new String[projectId.length];
|
|
|
+ for(int i=0;i<projectAuditorId.length; i++) {
|
|
|
+ projectAuditorId[i] = null;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ //检查项目是否截止
|
|
|
+ List<Integer> integers = Arrays.asList(projectId);
|
|
|
+ DateTimeFormatter localDtf = DateTimeFormatter.ofPattern("yyyy-MM-dd");
|
|
|
+ List<Project> projectList = projectMapper.selectList(new QueryWrapper<Project>().in("id", integers));
|
|
|
+ for (int i=0;i<projectId.length; i++) {
|
|
|
+ int pid = projectId[i];
|
|
|
+ Optional<Project> findP = projectList.stream().filter(p->p.getId().equals(pid)).findFirst();
|
|
|
+ if (findP.isPresent()) {
|
|
|
+ Project curP = findP.get();
|
|
|
+ if (!createDate[i].contains("@")) {
|
|
|
+ if (curP.getStatus() == 2) {
|
|
|
+ HttpRespMsg msg = new HttpRespMsg();
|
|
|
+ msg.setError("项目["+curP.getProjectName()+"]已完成。");
|
|
|
+ return msg;
|
|
|
+ }
|
|
|
+ if (curP.getStatus() == 3) {
|
|
|
+ HttpRespMsg msg = new HttpRespMsg();
|
|
|
+ msg.setError("项目["+curP.getProjectName()+"]已撤销。");
|
|
|
+ return msg;
|
|
|
+ }
|
|
|
+ if (curP.getPlanEndDate() != null && curP.getPlanEndDate().isBefore(LocalDate.parse(createDate[i], localDtf))) {
|
|
|
+ HttpRespMsg msg = new HttpRespMsg();
|
|
|
+ msg.setError("项目["+curP.getProjectName()+"]截止于"+localDtf.format(curP.getPlanEndDate())+",请修改。");
|
|
|
+ return msg;
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ //批量填报
|
|
|
+ String[] dateArr = createDate[i].split("@");
|
|
|
+ for (String curDate : dateArr) {
|
|
|
+ if (curP.getStatus() == 2) {
|
|
|
+ HttpRespMsg msg = new HttpRespMsg();
|
|
|
+ msg.setError("项目["+curP.getProjectName()+"]已完成。");
|
|
|
+ return msg;
|
|
|
+ }
|
|
|
+ if (curP.getStatus() == 3) {
|
|
|
+ HttpRespMsg msg = new HttpRespMsg();
|
|
|
+ msg.setError("项目["+curP.getProjectName()+"]已撤销。");
|
|
|
+ return msg;
|
|
|
+ }
|
|
|
+ if (curP.getPlanEndDate() != null && curP.getPlanEndDate().isBefore(LocalDate.parse(curDate, localDtf))) {
|
|
|
+ HttpRespMsg msg = new HttpRespMsg();
|
|
|
+ msg.setError("项目["+curP.getProjectName()+"]截止于"+localDtf.format(curP.getPlanEndDate())+",请修改。");
|
|
|
+ return msg;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ //自动填充项目审核人
|
|
|
+ for (int i=0;i<projectAuditorId.length; i++) {
|
|
|
+ if (projectAuditorId[i] == null) {
|
|
|
+ final int index = i;
|
|
|
+ projectAuditorId[i] = projectList.stream().filter(p->p.getId().equals(projectId[index])).findFirst().get().getInchargerId();
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ //代填
|
|
|
+ if (targetUids != null && targetUids.length > 0) {
|
|
|
+ String val = targetUids[0];
|
|
|
+ String[] ids = val.split("@");
|
|
|
+ targetUidList = new ArrayList<>();
|
|
|
+ for (int i = 0; i < ids.length; i++) {
|
|
|
+ targetUidList.add(ids[i]);
|
|
|
+ }
|
|
|
+ targetUserList = userService.list(new QueryWrapper<User>().in("id", targetUidList));
|
|
|
+ }
|
|
|
+ User user = userService.getById(token);
|
|
|
+ LocalDate now = LocalDate.now();
|
|
|
+ DateTimeFormatter dtf = DateTimeFormatter.ofPattern("yyyy-MM-dd");
|
|
|
+ BigDecimal hourCost = null;
|
|
|
+ //自己填写的情况,计算个人自己的时薪
|
|
|
+ if (targetUidList == null) {
|
|
|
+ if (user.getCostApplyDate() != null) {
|
|
|
+ //检查有效期
|
|
|
+ if (user.getCostApplyDate().compareTo(dtf.format(now)) > 0) {
|
|
|
+ //取上一个历史成本
|
|
|
+ List<UserSalary> list = userSalaryService.list(new QueryWrapper<UserSalary>().eq("user_id", user.getId()).orderByDesc("indate").last("limit 2"));
|
|
|
+ if (list.size() > 1) {
|
|
|
+ hourCost = list.get(1).getCost();
|
|
|
+ } else {
|
|
|
+ //没有记录,又没有达到预设的起效时间,则默认为0
|
|
|
+ hourCost = new BigDecimal(0);
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ hourCost = user.getCost();
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ hourCost = user.getCost();
|
|
|
+ }
|
|
|
+
|
|
|
+ if (hourCost == null) {
|
|
|
+ hourCost = new BigDecimal(0);
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ //代填的情况,计算每个人的时薪
|
|
|
+ for (User subsUser : targetUserList) {
|
|
|
+ BigDecimal tempCost = new BigDecimal(0);
|
|
|
+ if (subsUser.getCostApplyDate() != null) {
|
|
|
+ //检查有效期
|
|
|
+ if (subsUser.getCostApplyDate().compareTo(dtf.format(now)) > 0) {
|
|
|
+ //取上一个历史成本
|
|
|
+ List<UserSalary> list = userSalaryService.list(new QueryWrapper<UserSalary>().eq("user_id", subsUser.getId()).orderByDesc("indate").last("limit 2"));
|
|
|
+ if (list.size() > 1) {
|
|
|
+ tempCost = list.get(1).getCost();
|
|
|
+ } else {
|
|
|
+ //没有记录,又没有达到预设的起效时间,则默认为0
|
|
|
+ tempCost = new BigDecimal(0);
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ tempCost = subsUser.getCost();
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ tempCost = subsUser.getCost();
|
|
|
+ }
|
|
|
+
|
|
|
+ if (tempCost == null) {
|
|
|
+ tempCost = new BigDecimal(0);
|
|
|
+ }
|
|
|
+ //设置好时薪
|
|
|
+ subsUser.setCost(tempCost);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ SimpleDateFormat sdf = new SimpleDateFormat("HH:mm");
|
|
|
+ //判断当前操作的人员,是不是系统管理员
|
|
|
+ List<SysRichFunction> functionList = sysFunctionMapper.getRoleFunctions(user.getRoleId(), "代填日报");
|
|
|
+ if (functionList.size() == 0) {
|
|
|
+ //非系统管理员,检查填报时间
|
|
|
+ TimeType compTimeType = timeTypeMapper.selectById(user.getCompanyId());
|
|
|
+ Integer fillMonths = compTimeType.getFillMonths();
|
|
|
+
|
|
|
+ if (fillMonths > 0) {
|
|
|
+ //有限制的情况
|
|
|
+ LocalDate curMonth = LocalDate.now();
|
|
|
+ LocalDate targetDate = null;
|
|
|
+ if (fillMonths <=3) {
|
|
|
+ targetDate = curMonth.minusMonths(fillMonths-1);
|
|
|
+ targetDate = targetDate.withDayOfMonth(1);//修改日期为1号
|
|
|
+ } else if (fillMonths == 4) {
|
|
|
+ //7天内
|
|
|
+ targetDate = curMonth.minusDays(7);
|
|
|
+ }else if(fillMonths ==5){
|
|
|
+ //前一天
|
|
|
+ targetDate=curMonth.minusDays(1);
|
|
|
+ }
|
|
|
+
|
|
|
+ DateTimeFormatter dateTimeFormatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
|
|
|
+ //检查填报日期,是否早于限制的日期
|
|
|
+ boolean isForbidden = false;
|
|
|
+ if (createDate.length > 0) {
|
|
|
+ //日期都是一样的,取第一个就行了
|
|
|
+ String createDateOne = createDate[0];
|
|
|
+ if (createDateOne.contains("@")) {
|
|
|
+ String[] dateArray = createDateOne.split("@");
|
|
|
+ String startDate = dateArray[0];
|
|
|
+ LocalDate localStartDate = LocalDate.parse(startDate, dateTimeFormatter);
|
|
|
+ if (localStartDate.isBefore(targetDate)) {
|
|
|
+ isForbidden = true;
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ //单日填报,检查日期是否早于限制时间
|
|
|
+ if (LocalDate.parse(createDateOne, dateTimeFormatter).isBefore(targetDate)) {
|
|
|
+ isForbidden = true;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ if (isForbidden) {
|
|
|
+ HttpRespMsg msg = new HttpRespMsg();
|
|
|
+ msg.setError("补填日报不可早于"+dateTimeFormatter.format(targetDate)+",请联系系统管理员代填。");
|
|
|
+ return msg;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ try {
|
|
|
+ List<AuditWorkflowTimeSetting> auditWorkflowList
|
|
|
+ = auditWorkflowTimeSettingMapper.selectList(
|
|
|
+ new QueryWrapper<AuditWorkflowTimeSetting>().eq("dept_id", user.getDepartmentId()).orderByAsc("seq"));
|
|
|
+ List<Department> allDeptList = departmentMapper.selectList(new QueryWrapper<Department>().eq("company_id", user.getCompanyId()));
|
|
|
+
|
|
|
+ for (int i = 0; i < id.length; i++) {
|
|
|
+ if (createDate[i].contains("@")) {
|
|
|
+ DateTimeFormatter mdFormatter = DateTimeFormatter.ofPattern("MM-dd");
|
|
|
+ System.out.println("============这是批量填报=");
|
|
|
+ //这是批量填报的情况,日期有范围
|
|
|
+ String[] dateArray = createDate[i].split("@");
|
|
|
+ String startDate = dateArray[0];
|
|
|
+ String endDate = dateArray[1];
|
|
|
+ //检查该时间范围是否已经有填写过的日报了
|
|
|
+ List<Report> oldReportList = reportService.list(new QueryWrapper<Report>().between("create_date", startDate, endDate).eq("creator_id", token));
|
|
|
+ if (oldReportList.size() > 0) {
|
|
|
+ List<LocalDate> collect = oldReportList.stream().map(Report::getCreateDate).collect(Collectors.toList());
|
|
|
+ StringBuilder sb = new StringBuilder();
|
|
|
+ collect.forEach(c->{
|
|
|
+ sb.append(mdFormatter.format(c)).append(",");
|
|
|
+ });
|
|
|
+ String s = sb.toString();
|
|
|
+ s = s.substring(0, s.length() -1);
|
|
|
+ HttpRespMsg msg = new HttpRespMsg();
|
|
|
+ msg.setError("已存在填写日报: " + s+", 请重新选择日期范围");
|
|
|
+ return msg;
|
|
|
+ }
|
|
|
+
|
|
|
+// LocalDate localStartDate = LocalDate.parse(startDate, ddtf);
|
|
|
+// LocalDate localEndDate = LocalDate.parse(endDate, ddtf);
|
|
|
+ List<LocalDate> workDaysListInRange = WorkDayCalculateUtils.getWorkDaysListInRange(startDate, endDate);
|
|
|
+ //获取当前填报人所在部门的自定义审核流程
|
|
|
+ for (LocalDate localStartDate : workDaysListInRange) {
|
|
|
+ if (targetUserList == null) {
|
|
|
+ Report report = new Report();
|
|
|
+ report.setId(id[i] == -1 ? null : id[i]);
|
|
|
+ report.setProjectId(projectId[i]);
|
|
|
+ report.setSubProjectId(subProjectId[i]);
|
|
|
+ report.setGroupId(groupId[i]);
|
|
|
+ report.setReportTimeType(reportTimeType[i]);
|
|
|
+ report.setMultiWorktime(multiWorktime[i]);
|
|
|
+ report.setContent(content[i]);
|
|
|
+ report.setDegreeId(degreeId.length > 0?degreeId[i]:null);
|
|
|
+ report.setCustomData(customData[i]);
|
|
|
+ report.setState(draft==0?0:3);
|
|
|
+ report.setCompanyId(user.getCompanyId());
|
|
|
+ report.setPicAdd(pics!=null?pics[i]:null);
|
|
|
+ report.setStage(stage[i]);
|
|
|
+ report.setCreateDate(localStartDate);
|
|
|
+ report.setCreatorId(token);
|
|
|
+ report.setProjectAuditState(0);
|
|
|
+ report.setProjectAuditorId(projectAuditorId[i]);
|
|
|
+ if (auditWorkflowList.size() == 0) {
|
|
|
+ //没有自定义审核流,默认的直接是项目负责人审核
|
|
|
+ report.setIsDeptAudit(0);
|
|
|
+ report.setIsFinalAudit(1);
|
|
|
+ } else {
|
|
|
+ //取第一个审核节点
|
|
|
+ AuditWorkflowTimeSetting firstNode = auditWorkflowList.get(0);
|
|
|
+ report.setIsFinalAudit(auditWorkflowList.size() > 1?0:1);
|
|
|
+ report.setIsDeptAudit(firstNode.getIsDeptAudit());
|
|
|
+ report.setAuditDeptid(firstNode.getAuditDeptId());
|
|
|
+ report.setAuditDeptManagerid(firstNode.getAuditDeptId() != null?allDeptList.stream().filter(d->d.getDepartmentId().equals(firstNode.getAuditDeptId())).findFirst().get().getManagerId(): null);
|
|
|
+ }
|
|
|
+ if (taskId != null && taskId[i] != null && taskId[i] != 0) {
|
|
|
+ report.setTaskId(taskId[i]);
|
|
|
+ }
|
|
|
+ if (isOvertime != null && isOvertime[i] != null) {
|
|
|
+ report.setIsOvertime(isOvertime[i]);
|
|
|
+ }
|
|
|
+ if (progress != null && progress[i] != null) {
|
|
|
+ report.setProgress(progress[i]);
|
|
|
+ }
|
|
|
+ //计算工时和成本
|
|
|
+ if (report.getMultiWorktime() == 0) {
|
|
|
+ fillReportHours(report, hourCost, workingTime==null?null:workingTime[i], timeType==null?null:timeType[i], startTime==null?null:startTime[i], endTime==null?null:endTime[i], sdf);
|
|
|
+ } else {
|
|
|
+ fillReportHours(report, hourCost, workingTime==null?null:workingTime[i], timeType==null?null:timeType[i], null, null, sdf);
|
|
|
+ }
|
|
|
+
|
|
|
+ //项目专业的进展
|
|
|
+ fillReportProgress(report, professionProgress[i]);
|
|
|
+ reportList.add(report);
|
|
|
+ } else {
|
|
|
+ //批量代填报的
|
|
|
+ for (User subsUser : targetUserList) {
|
|
|
+ Report report = new Report()
|
|
|
+ .setId(id[i] == -1 ? null : id[i])
|
|
|
+ .setProjectId(projectId[i])
|
|
|
+ .setSubProjectId(subProjectId[i])
|
|
|
+ .setGroupId(groupId[i])
|
|
|
+ .setReportTimeType(reportTimeType[i])
|
|
|
+ .setMultiWorktime(multiWorktime[i])
|
|
|
+ .setContent(content[i])
|
|
|
+ .setDegreeId(degreeId.length > 0?degreeId[i]:null)
|
|
|
+ .setCustomData(customData[i])
|
|
|
+ .setStage(stage[i])
|
|
|
+ .setState(1)//代填,直接是审核通过状态
|
|
|
+ .setCompanyId(user.getCompanyId())
|
|
|
+ .setPicAdd(pics!=null?pics[i]:null)
|
|
|
+ .setCreateDate(localStartDate)
|
|
|
+ .setCreatorId(subsUser.getId())
|
|
|
+ .setProjectAuditorId(projectAuditorId[i]);;
|
|
|
+ report.setProjectAuditState(0);
|
|
|
+ if (auditWorkflowList.size() == 0) {
|
|
|
+ //没有自定义审核流,默认的直接是项目负责人审核
|
|
|
+ report.setIsDeptAudit(0);
|
|
|
+ report.setIsFinalAudit(1);
|
|
|
+ } else {
|
|
|
+ //取第一个审核节点
|
|
|
+ AuditWorkflowTimeSetting firstNode = auditWorkflowList.get(0);
|
|
|
+ report.setIsFinalAudit(auditWorkflowList.size() > 1?0:1);
|
|
|
+ report.setIsDeptAudit(firstNode.getIsDeptAudit());
|
|
|
+ report.setAuditDeptid(firstNode.getAuditDeptId());
|
|
|
+ report.setAuditDeptManagerid(firstNode.getAuditDeptId() != null?allDeptList.stream().filter(d->d.getDepartmentId().equals(firstNode.getAuditDeptId())).findFirst().get().getManagerId(): null);
|
|
|
+ }
|
|
|
+ if (taskId != null && taskId[i] != null && taskId[i] != 0) {
|
|
|
+ report.setTaskId(taskId[i]);
|
|
|
+ }
|
|
|
+ if (isOvertime != null && isOvertime[i] != null) {
|
|
|
+ report.setIsOvertime(isOvertime[i]);
|
|
|
+ }
|
|
|
+ if (progress != null && progress[i] != null) {
|
|
|
+ report.setProgress(progress[i]);
|
|
|
+ }
|
|
|
+ //计算工时和成本
|
|
|
+ if (report.getMultiWorktime() == 0) {
|
|
|
+ fillReportHours(report, hourCost, workingTime==null?null:workingTime[i], timeType==null?null:timeType[i], startTime==null?null:startTime[i], endTime==null?null:endTime[i], sdf);
|
|
|
+ } else {
|
|
|
+ fillReportHours(report, hourCost, workingTime==null?null:workingTime[i], timeType==null?null:timeType[i], null, null, sdf);
|
|
|
+ }
|
|
|
+
|
|
|
+ fillReportProgress(report, professionProgress[i]);
|
|
|
+ reportList.add(report);
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ if (targetUidList == null) {
|
|
|
+ Report report = new Report();
|
|
|
+ report.setId(id[i] == -1 ? null : id[i]);
|
|
|
+ report.setProjectId(projectId[i]);
|
|
|
+ report.setSubProjectId(subProjectId[i]);
|
|
|
+ report.setGroupId(groupId[i]);
|
|
|
+ report.setReportTimeType(reportTimeType[i]);
|
|
|
+ report.setMultiWorktime(multiWorktime.length > 0?multiWorktime[i]:0);
|
|
|
+ report.setContent(content.length > 0?content[i]:"-");
|
|
|
+ report.setDegreeId(degreeId.length > 0?degreeId[i]:null);
|
|
|
+ report.setCustomData(customData[i]);
|
|
|
+ report.setStage(stage != null && stage.length>0?stage[i]:"-");
|
|
|
+ report.setState(draft==0?0:3);
|
|
|
+ report.setCompanyId(user.getCompanyId());
|
|
|
+ report.setPicAdd(pics!=null && pics.length>0?pics[i]:null);
|
|
|
+ report.setCreateDate(LocalDate.parse(createDate[i], DateTimeFormatter.ofPattern("yyyy-MM-dd")));
|
|
|
+ report.setCreatorId(token);
|
|
|
+ report.setProjectAuditState(0);
|
|
|
+ report.setProjectAuditorId(projectAuditorId[i]);
|
|
|
+ if (auditWorkflowList.size() == 0) {
|
|
|
+ //没有自定义审核流,默认的直接是项目负责人审核
|
|
|
+ report.setIsDeptAudit(0);
|
|
|
+ report.setIsFinalAudit(1);
|
|
|
+ } else {
|
|
|
+ //取第一个审核节点
|
|
|
+ AuditWorkflowTimeSetting firstNode = auditWorkflowList.get(0);
|
|
|
+ report.setIsFinalAudit(auditWorkflowList.size() > 1?0:1);
|
|
|
+ report.setIsDeptAudit(firstNode.getIsDeptAudit());
|
|
|
+ report.setAuditDeptid(firstNode.getAuditDeptId());
|
|
|
+ report.setAuditDeptManagerid(firstNode.getAuditDeptId() != null?allDeptList.stream().filter(d->d.getDepartmentId().equals(firstNode.getAuditDeptId())).findFirst().get().getManagerId(): null);
|
|
|
+ }
|
|
|
+ if (taskId != null && taskId[i] != null && taskId[i] != 0) {
|
|
|
+ report.setTaskId(taskId[i]);
|
|
|
+ }
|
|
|
+ if (isOvertime != null && isOvertime[i] != null) {
|
|
|
+ report.setIsOvertime(isOvertime[i]);
|
|
|
+ }
|
|
|
+ if (progress != null && progress[i] != null) {
|
|
|
+ report.setProgress(progress[i]);
|
|
|
+ }
|
|
|
+ //计算工时和成本
|
|
|
+ if (report.getMultiWorktime() == 0) {
|
|
|
+ fillReportHours(report, hourCost, workingTime==null?null:workingTime[i], timeType==null?null:timeType[i], startTime==null?null:startTime[i], endTime==null?null:endTime[i], sdf);
|
|
|
+ } else {
|
|
|
+ fillReportHours(report, hourCost, workingTime==null?null:workingTime[i], timeType==null?null:timeType[i], null, null, sdf);
|
|
|
+ }
|
|
|
+
|
|
|
+ fillReportProgress(report, professionProgress[i]);
|
|
|
+ reportList.add(report);
|
|
|
+ /*后续需要加入状态*/
|
|
|
+ if (createDate[i] == null || projectId[i] == null) {
|
|
|
+ HttpRespMsg httpRespMsg = new HttpRespMsg();
|
|
|
+ httpRespMsg.setError("缺少数据");
|
|
|
+ return httpRespMsg;
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ //批量代填的情况
|
|
|
+ for (User subsUser : targetUserList) {
|
|
|
+ Report report = new Report()
|
|
|
+ .setId(id[i] == -1 ? null : id[i])
|
|
|
+ .setProjectId(projectId[i])
|
|
|
+ .setSubProjectId(subProjectId[i])
|
|
|
+ .setGroupId(groupId[i])
|
|
|
+ .setReportTimeType(reportTimeType[i])
|
|
|
+ .setMultiWorktime(multiWorktime[i])
|
|
|
+ .setContent(content[i])
|
|
|
+ .setDegreeId(degreeId.length > 0?degreeId[i]:null)
|
|
|
+ .setCustomData(customData[i])
|
|
|
+ .setStage(stage[i])
|
|
|
+// .setState(auditWorkflowList.size() == 0?1:0)//代填的如果没有自定义审核流程就直接审核通过了
|
|
|
+ .setCompanyId(user.getCompanyId())
|
|
|
+ .setPicAdd(pics!=null?pics[i]:null)
|
|
|
+ .setCreateDate(LocalDate.parse(createDate[i], DateTimeFormatter.ofPattern("yyyy-MM-dd")))
|
|
|
+ .setCreatorId(subsUser.getId())
|
|
|
+ .setProjectAuditorId(projectAuditorId[i])
|
|
|
+ .setFillUserid(token);
|
|
|
+ report.setProjectAuditState(1);
|
|
|
+ if (auditWorkflowList.size() == 0) {
|
|
|
+ //没有自定义审核流,直接代填的,就算审核通过
|
|
|
+ report.setIsDeptAudit(0);
|
|
|
+ report.setIsFinalAudit(1);
|
|
|
+ report.setState(1);
|
|
|
+ } else {
|
|
|
+ //有审核流程的,取项目经理后面的流程节点
|
|
|
+ int projectLeaderNodeIndex = 0;
|
|
|
+ for (int t=0;t<auditWorkflowList.size(); t++) {
|
|
|
+ if (auditWorkflowList.get(t).getIsDeptAudit() == 0) {
|
|
|
+ projectLeaderNodeIndex = t;
|
|
|
+ break;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ if (projectLeaderNodeIndex == auditWorkflowList.size() -1) {
|
|
|
+ //最后一个节点就是项目经理,那就不用审核了,直接通过
|
|
|
+ report.setState(1);
|
|
|
+ } else {
|
|
|
+ //否则取下一个节点,待审核
|
|
|
+ report.setState(0);
|
|
|
+ int nextIndex = projectLeaderNodeIndex + 1;
|
|
|
+ AuditWorkflowTimeSetting nextNode = auditWorkflowList.get(nextIndex);
|
|
|
+ report.setIsFinalAudit((nextIndex == auditWorkflowList.size()-1)?1:0);
|
|
|
+ report.setIsDeptAudit(nextNode.getIsDeptAudit());
|
|
|
+ report.setAuditDeptid(nextNode.getAuditDeptId());
|
|
|
+ report.setAuditDeptManagerid(nextNode.getAuditDeptId() != null?allDeptList.stream().filter(d->d.getDepartmentId().equals(nextNode.getAuditDeptId())).findFirst().get().getManagerId(): null);
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ if (taskId != null && taskId[i] != null && taskId[i] != 0) {
|
|
|
+ report.setTaskId(taskId[i]);
|
|
|
+ }
|
|
|
+ if (isOvertime != null && isOvertime[i] != null) {
|
|
|
+ report.setIsOvertime(isOvertime[i]);
|
|
|
+ }
|
|
|
+ if (progress != null && progress[i] != null) {
|
|
|
+ report.setProgress(progress[i]);
|
|
|
+ }
|
|
|
+ hourCost = subsUser.getCost();
|
|
|
+ //计算工时和成本
|
|
|
+ if (report.getMultiWorktime() == 0) {
|
|
|
+ fillReportHours(report, hourCost, workingTime==null?null:workingTime[i], timeType==null?null:timeType[i], startTime==null?null:startTime[i], endTime==null?null:endTime[i], sdf);
|
|
|
+ } else {
|
|
|
+ fillReportHours(report, hourCost, workingTime==null?null:workingTime[i], timeType==null?null:timeType[i], null, null, sdf);
|
|
|
+ }
|
|
|
+
|
|
|
+ fillReportProgress(report, professionProgress[i]);
|
|
|
+ reportList.add(report);
|
|
|
+ /*后续需要加入状态*/
|
|
|
+ if (createDate[i] == null || projectId[i] == null) {
|
|
|
+ HttpRespMsg httpRespMsg = new HttpRespMsg();
|
|
|
+ httpRespMsg.setError("缺少数据");
|
|
|
+ return httpRespMsg;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+ } catch (NullPointerException e) {
|
|
|
+ e.printStackTrace();
|
|
|
+ HttpRespMsg httpRespMsg = new HttpRespMsg();
|
|
|
+ httpRespMsg.setError("验证失败");
|
|
|
+ return httpRespMsg;
|
|
|
+ }
|
|
|
+ //校验工作时长
|
|
|
+ for (Report report : reportList) {
|
|
|
+ if (report.getWorkingTime() == null || report.getWorkingTime() <= 0.0) {
|
|
|
+ HttpRespMsg httpRespMsg = new HttpRespMsg();
|
|
|
+ httpRespMsg.setError("请填写工作时长");
|
|
|
+ return httpRespMsg;
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ return reportService.editReport(reportList, createDate.length > 0 ? createDate[0] : null, targetUserList, hourCost, user.getCompanyId());
|
|
|
+ }
|
|
|
+
|
|
|
+ private void fillReportHours(Report report, BigDecimal hourCost, Double workingTime, Integer timeType, String startTime, String endTime, SimpleDateFormat sdf) {
|
|
|
+ if (report.getMultiWorktime() == 0) {
|
|
|
+ //普通工时成本计算
|
|
|
+ if (report.getReportTimeType() == 0) {
|
|
|
+ report.setWorkingTime(workingTime)
|
|
|
+ .setCost(hourCost.multiply(new BigDecimal(workingTime)))
|
|
|
+ .setTimeType(timeType);
|
|
|
+ } else if (report.getReportTimeType() == 1|| report.getReportTimeType() == 3) {
|
|
|
+ report.setWorkingTime(workingTime)
|
|
|
+ .setCost(hourCost.multiply(new BigDecimal(workingTime)));
|
|
|
+ } else if (report.getReportTimeType() == 2) {
|
|
|
+ //时间范围填报, 计算一下时长
|
|
|
+ try {
|
|
|
+ report.setStartTime(startTime).setEndTime(endTime);
|
|
|
+ long time = sdf.parse(report.getEndTime()).getTime() - sdf.parse(report.getStartTime()).getTime();
|
|
|
+ int minutes = (int)time/1000/60;
|
|
|
+ double hours = minutes*1.0f/60;
|
|
|
+ report.setWorkingTime(hours);
|
|
|
+ report.setCost(hourCost.multiply(new BigDecimal(hours)));
|
|
|
+ } catch (ParseException e) {
|
|
|
+ e.printStackTrace();
|
|
|
+ }
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ //getMultiWorktime==1, content中含有多个工时
|
|
|
+ String str = report.getContent().replaceAll("@",",");
|
|
|
+ JSONArray array = JSONArray.parseArray(str);
|
|
|
+ try {
|
|
|
+ double totalHours = 0;
|
|
|
+ for (int t=0;t<array.size(); t++) {
|
|
|
+ JSONObject jsonObject = array.getJSONObject(t);
|
|
|
+ WorktimeItem item = JSONObject.toJavaObject(jsonObject, WorktimeItem.class);
|
|
|
+ long time = sdf.parse(item.getEndTime()).getTime() - sdf.parse(item.getStartTime()).getTime();
|
|
|
+ int minutes = (int)time/1000/60;
|
|
|
+ double hours = minutes*1.0f/60;
|
|
|
+ item.setTime(hours);
|
|
|
+ jsonObject.put("time", hours);
|
|
|
+ totalHours += hours;
|
|
|
+ }
|
|
|
+ report.setWorkingTime(totalHours);
|
|
|
+ report.setCost(hourCost.multiply(new BigDecimal(totalHours)));
|
|
|
+ report.setContent(array.toJSONString());
|
|
|
+ } catch (ParseException e) {
|
|
|
+ e.printStackTrace();
|
|
|
+ }
|
|
|
+ }
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 删除报告
|
|
|
+ * id 要删除的报告的id
|
|
|
+ */
|
|
|
+ @RequestMapping("/delete")
|
|
|
+ public HttpRespMsg deleteReport(String userId, String date) {
|
|
|
+ return reportService.deleteReport(userId, date);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 根据审核状态获取报告
|
|
|
+ * state 筛选状态 0-未审核 1-已通过 2-未通过
|
|
|
+ */
|
|
|
+ @RequestMapping("/listByState")
|
|
|
+ public HttpRespMsg getListByState(@RequestParam Integer state,
|
|
|
+ Integer departmentId,
|
|
|
+ Integer projectId,
|
|
|
+ String date,
|
|
|
+ String startDate,
|
|
|
+ String endDate,
|
|
|
+ String userId,
|
|
|
+ HttpServletRequest request) {
|
|
|
+ return reportService.getListByState(state, departmentId,
|
|
|
+ projectId,
|
|
|
+ date, startDate, endDate, userId,
|
|
|
+ request);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 获取专业待审核的报告
|
|
|
+ * @param state
|
|
|
+ * @param departmentId
|
|
|
+ * @param projectId
|
|
|
+ * @param date
|
|
|
+ * @param request
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ @RequestMapping("/listByStateProfession")
|
|
|
+ public HttpRespMsg listByStateProfession(@RequestParam Integer state,
|
|
|
+ Integer departmentId,
|
|
|
+ Integer projectId,
|
|
|
+ String date,
|
|
|
+ HttpServletRequest request) {
|
|
|
+ return reportService.listByStateProfession(state, departmentId,
|
|
|
+ projectId,
|
|
|
+ date,request);
|
|
|
+ }
|
|
|
+
|
|
|
+ @RequestMapping("/listByStateDepartment")
|
|
|
+ public HttpRespMsg listByStateDepartment(@RequestParam Integer state,
|
|
|
+ Integer projectId,
|
|
|
+ String date,
|
|
|
+ HttpServletRequest request) {
|
|
|
+ return reportService.listByStateDepartment(state,
|
|
|
+ projectId,
|
|
|
+ date,request);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 按某人某日期审批通过报告
|
|
|
+ * id 要通过的报告的用户id
|
|
|
+ * reportIds 报告id
|
|
|
+ */
|
|
|
+ @RequestMapping("/approve")
|
|
|
+ public HttpRespMsg approveReport(@RequestParam String reportIds, Integer isDepartment, HttpServletRequest request) {
|
|
|
+ return reportService.approveReport(reportIds,isDepartment, request);
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 按某人某日期审批未通过报告 撤销通过报告
|
|
|
+ * id 要未通过的报告的用户id
|
|
|
+ * date 日期 格式yyyy-mm-dd
|
|
|
+ */
|
|
|
+ @RequestMapping("/deny")
|
|
|
+ public HttpRespMsg denyReport(@RequestParam String date, @RequestParam String reportIds, String reason, Integer isDepartment, HttpServletRequest request) {
|
|
|
+ return reportService.denyReport(date,reportIds, reason, isDepartment, request);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 撤回报告
|
|
|
+ * @param reportIds
|
|
|
+ * @param request
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ @RequestMapping("/cancel")
|
|
|
+ public HttpRespMsg cancelReport(@RequestParam String userId, @RequestParam String reportIds,HttpServletRequest request) {
|
|
|
+ return reportService.cancelReport(userId, reportIds, request);
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ @RequestMapping("/getMembList")
|
|
|
+ public HttpRespMsg getMembList(@RequestParam(required=false) String date, Integer manageDeptId, HttpServletRequest request) {
|
|
|
+ if (date == null) {
|
|
|
+ //默认获取今天的
|
|
|
+ date = new SimpleDateFormat("yyyy-MM-dd").format(new Date());
|
|
|
+ }
|
|
|
+ return reportService.getMembList(date, manageDeptId, request);
|
|
|
+ }
|
|
|
+
|
|
|
+ @RequestMapping("/batchApproveReport")
|
|
|
+ public HttpRespMsg batchApproveReport(@RequestParam String ids, Integer isDepartment, HttpServletRequest request) {
|
|
|
+ return reportService.batchApproveReport(ids, isDepartment, request);
|
|
|
+ }
|
|
|
+
|
|
|
+ @RequestMapping("/batchDenyReport")
|
|
|
+ public HttpRespMsg batchDenyReport(@RequestParam String ids, Integer isDepartment, HttpServletRequest request) {
|
|
|
+ return reportService.batchDenyReport(ids, isDepartment, request);
|
|
|
+ }
|
|
|
+
|
|
|
+ @RequestMapping("/getUserDailyWorkTime")
|
|
|
+ public HttpRespMsg getUserDailyWorkTime(HttpServletRequest request, String startDate, String endDate) {
|
|
|
+ return reportService.getUserDailyWorkTime(request, startDate, endDate);
|
|
|
+ }
|
|
|
+
|
|
|
+ @RequestMapping("/getNoReportUserList")
|
|
|
+ public HttpRespMsg getNoReportUserList(HttpServletRequest request, String startDate, String endDate) {
|
|
|
+ return reportService.getNoReportUserList(request, startDate, endDate);
|
|
|
+ }
|
|
|
+
|
|
|
+ @RequestMapping("/exportNoReportUserList")
|
|
|
+ public HttpRespMsg exportNoReportUserList(HttpServletRequest request, String startDate, String endDate) {
|
|
|
+ return reportService.exportNoReportUserList(request, startDate, endDate);
|
|
|
+ }
|
|
|
+
|
|
|
+ @RequestMapping("/exportUserDailyWorkTime")
|
|
|
+ public HttpRespMsg exportUserDailyWorkTime(HttpServletRequest request, String startDate, String endDate) {
|
|
|
+ return reportService.exportUserDailyWorkTime(request, startDate, endDate);
|
|
|
+ }
|
|
|
+
|
|
|
+ /**
|
|
|
+ * 计算给定时间段内的工作日数量
|
|
|
+ * @param startDate 开始日期
|
|
|
+ * @param endDate 结束日期
|
|
|
+ * @return
|
|
|
+ */
|
|
|
+ @RequestMapping("/getWorkDays")
|
|
|
+ public HttpRespMsg getWorkDays(String startDate, String endDate) {
|
|
|
+ HttpRespMsg msg = new HttpRespMsg();
|
|
|
+ msg.data = WorkDayCalculateUtils.getWorkDaysCountInRange(startDate, endDate);
|
|
|
+ return msg;
|
|
|
+ }
|
|
|
+
|
|
|
+
|
|
|
+ @RequestMapping("/importData")
|
|
|
+ public HttpRespMsg importData(Integer companyId, Integer withCheckIn,
|
|
|
+ MultipartFile file, HttpServletRequest request) {
|
|
|
+ return reportService.importData(companyId,withCheckIn, file, request);
|
|
|
+ }
|
|
|
+
|
|
|
+ @RequestMapping("/listImportByState")
|
|
|
+ public HttpRespMsg listDeptImportByState(
|
|
|
+ Integer projectId,
|
|
|
+ @RequestParam(required = false, defaultValue = "0") Integer dateType,
|
|
|
+ String date,
|
|
|
+ Integer departmentId,
|
|
|
+ HttpServletRequest request) {
|
|
|
+ String token = request.getHeader("TOKEN");
|
|
|
+ User user = userService.getById(token);
|
|
|
+ return reportService.listDeptImportByState(user.getId(),
|
|
|
+ projectId,dateType,
|
|
|
+ date, departmentId, request);
|
|
|
+ }
|
|
|
+
|
|
|
+ @RequestMapping("/getlastWeekFillTime")
|
|
|
+ public HttpRespMsg getlastWeekFillTime(String userId) {
|
|
|
+ return reportService.getlastWeekFillTime(userId);
|
|
|
+ }
|
|
|
+}
|
|
|
+
|