package org.jeecg.modules.weekly.service.impl;
|
|
|
import com.alibaba.fastjson.JSON;
|
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
|
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
|
import org.apache.commons.lang3.StringUtils;
|
import org.apache.shiro.SecurityUtils;
|
import org.jeecg.common.api.vo.Result;
|
import org.jeecg.common.constant.CacheConstant;
|
import org.jeecg.common.system.vo.LoginUser;
|
import org.jeecg.common.util.DateUtils;
|
import org.jeecg.common.util.HTMLUtils;
|
import org.jeecg.common.util.RedisUtil;
|
import org.jeecg.modules.weekly.entity.*;
|
import org.jeecg.modules.weekly.entity.ProProject;
|
import org.jeecg.modules.weekly.feign.ProjectClient;
|
import org.jeecg.modules.weekly.mapper.WekEvaluateMapper;
|
import org.jeecg.modules.weekly.mapper.WekRecordMapper;
|
import org.jeecg.modules.weekly.service.IWekRecordService;
|
import org.jeecg.modules.weekly.vo.*;
|
import org.springframework.beans.BeanUtils;
|
import org.springframework.beans.factory.annotation.Autowired;
|
import org.springframework.stereotype.Service;
|
import org.springframework.transaction.annotation.Transactional;
|
|
import java.lang.reflect.Field;
|
import java.text.NumberFormat;
|
import java.text.SimpleDateFormat;
|
import java.time.LocalDate;
|
import java.time.temporal.TemporalAdjusters;
|
import java.util.*;
|
import java.util.concurrent.atomic.AtomicBoolean;
|
import java.util.concurrent.atomic.AtomicInteger;
|
import java.util.concurrent.atomic.AtomicReference;
|
import java.util.stream.Collectors;
|
import java.util.stream.IntStream;
|
|
|
/**
|
* 周报记录
|
* <p>
|
* 注:1、查询个人周报时会查询一年的每一周,没数据则显示空列表
|
* methods: queryWeeklyListByWeekNo
|
* 2、查询部门周报或项目周报时只查询有数据的周,不查询空数据
|
* methods: queryDepartUserWeeklyList、queryProjectWeekly、queryAllProjectWeekly
|
*/
|
@Service
|
public class WekRecordServiceImpl extends ServiceImpl<WekRecordMapper, WekRecord> implements IWekRecordService {
|
@Autowired
|
private WekRecordMapper wekRecordMapper;
|
@Autowired
|
private WekEvaluateMapper wekEvaluateMapper;
|
@Autowired
|
private RedisUtil redisUtil;
|
@Autowired
|
private ProjectClient projectClient;
|
|
|
@Override
|
@Transactional
|
public void insertBatch(WekResultBean resultBean) {
|
LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
|
List<WekWeekBean> weekList = resultBean.getWeekList();
|
for (int i = 0; i < weekList.size(); i++) {
|
WekWeekBean weekBean = weekList.get(i);
|
if (weekBean == null) continue;
|
List<WekTypeBean> typeList = weekBean.getTypeList();
|
if (typeList == null) continue;
|
for (int j = 0; j < typeList.size(); j++) {
|
WekTypeBean typeBean = typeList.get(j);
|
if (typeBean == null) continue;
|
List<WekRecord> wekList = typeBean.getWekList();
|
if (wekList == null || wekList.size() < 1) continue;
|
wekList.forEach((item) -> {
|
item.setUser(sysUser.getUsername());
|
item.setYearWeek(item.getYear() * 100 + item.getWeek());
|
});
|
saveOrUpdateBatch(wekList);
|
|
}
|
}
|
|
|
}
|
|
@Override
|
public List<WekWeekBean> querySingleThisWeek(WekRecord wekRecord) {
|
LoginUser sysUser = (LoginUser) SecurityUtils.getSubject().getPrincipal();
|
int curWeek = DateUtils.getCurWeek();
|
int curYear = DateUtils.getCurYear();
|
|
//查询本周和上周数据
|
List<WekRecord> list = new ArrayList<>();
|
if (curWeek != 1) {
|
int arr[] = {curWeek, curWeek - 1};
|
QueryWrapper<WekRecord> queryWrapper = new QueryWrapper<>();
|
queryWrapper.lambda().eq(WekRecord::getYear, curYear).eq(WekRecord::getUser, sysUser.getUsername()).and(j -> j.in(WekRecord::getWeek, arr[0], arr[1]));
|
queryWrapper.lambda().orderByAsc(WekRecord::getCreateTime);
|
List<WekRecord> list1 = this.list(queryWrapper);
|
list.addAll(list1);
|
} else {
|
QueryWrapper<WekRecord> queryWrapper2 = new QueryWrapper<>();
|
queryWrapper2.lambda().eq(WekRecord::getYear, curYear - 1).eq(WekRecord::getUser, sysUser.getUsername()).and(j -> j.in(WekRecord::getWeek, 52));
|
queryWrapper2.lambda().orderByAsc(WekRecord::getCreateTime);
|
List<WekRecord> list2 = this.list(queryWrapper2);
|
list.addAll(list2);
|
|
|
QueryWrapper<WekRecord> queryWrapper = new QueryWrapper<>();
|
queryWrapper.lambda().eq(WekRecord::getYear, curYear).eq(WekRecord::getUser, sysUser.getUsername()).and(j -> j.in(WekRecord::getWeek, 1));
|
queryWrapper.lambda().orderByAsc(WekRecord::getCreateTime);
|
List<WekRecord> list1 = this.list(queryWrapper);
|
list.addAll(list1);
|
|
|
}
|
|
|
//自动录入
|
autoEnter(list, curWeek,curYear);
|
|
|
//根据周和数据类型分类
|
Map<Integer, Map<Integer, List<WekRecord>>> collect = list.stream().collect(Collectors.groupingBy(t -> t.getWeek(), Collectors.groupingBy(t -> t.getType())));
|
List<WekWeekBean> templateData = createTemplateData();
|
|
/**
|
* 将周报信息填充到模板中
|
*/
|
//周
|
for (Map.Entry<Integer, Map<Integer, List<WekRecord>>> entry : collect.entrySet()) {
|
for (int i = 0; i < templateData.size(); i++) {
|
WekWeekBean week = templateData.get(i);
|
week.setUsername(sysUser.getUsername());
|
week.setShowDetail(true);
|
|
if (entry.getKey() == week.getWeek()) {
|
Map<Integer, List<WekRecord>> typeMap = entry.getValue();
|
List<WekTypeBean> typeList = week.getTypeList();
|
//周报类型 0-本周周报 1-本周计划外 2-下周计划 3-下周需协调
|
for (Map.Entry<Integer, List<WekRecord>> type : typeMap.entrySet()) {
|
for (int j = 0; j < typeList.size(); j++) {
|
|
WekTypeBean typeBean = typeList.get(j);
|
if (typeBean.getWeek() == week.getWeek() && typeBean.getType() == type.getKey()) {
|
typeBean.getWekList().addAll(type.getValue());
|
}
|
}
|
|
}
|
}
|
}
|
|
}
|
return templateData;
|
}
|
|
/**
|
* 本周周报自动录入上周下周计划内容
|
*
|
* @param list 本周和上周周报记录
|
* @param curWeek 当前周号
|
*/
|
private void autoEnter(List<WekRecord> list, int curWeek,int curYear) {
|
//TODO 上周计划填充到本周内容(思想:本周周报内容没有记录的时候,查询上周计划填充,只填充不做真实保存,用户编辑本周周报保存后再真实保存)
|
//1.0本周周报内容
|
List<WekRecord> tWeekList = list.stream().filter(i -> i.getWeek() == curWeek).collect(Collectors.toList());
|
//1.1上周周报内容
|
List<WekRecord> lWeekList = new ArrayList<>();
|
if (curWeek != 1) {
|
List<WekRecord> collect = list.stream().filter(i -> i.getWeek() == (curWeek - 1)).collect(Collectors.toList());
|
lWeekList.addAll(collect);
|
} else {
|
List<WekRecord> collect = list.stream().filter(i -> i.getWeek() == 52).collect(Collectors.toList());
|
lWeekList.addAll(collect);
|
}
|
|
|
//2.0本周没有周报记录
|
if (tWeekList.isEmpty()) {
|
//2.1上周有数据
|
if (!lWeekList.isEmpty()) {
|
//type = 2 下周计划
|
List<WekRecord> nList = lWeekList.stream().filter(i -> i.getType() == 2).collect(Collectors.toList());
|
//2.2上周周报存在下周计划数据
|
if (!nList.isEmpty()) {
|
for (int i = 0; i < nList.size(); i++) {
|
WekRecord record = nList.get(i);
|
WekRecord item = new WekRecord();
|
//将上周周报的下周计划 填充到本周周报内容
|
BeanUtils.copyProperties(record, item);
|
item.setId(UUID.randomUUID().toString().replace("-", ""));
|
item.setWeek(curWeek);
|
item.setYear(curYear);
|
item.setYearWeek(item.getYear() * 100 + item.getWeek());
|
item.setType(0);
|
item.setCreateTime(DateUtils.minusSeconds(nList.size()-i));
|
item.setUpdateTime(null);
|
list.add(item);
|
}
|
}
|
}
|
}
|
}
|
|
@Override
|
public List<WekWeekBean> queryWeeklyListByWeekNo(Integer year, Integer week, String username) {
|
|
List<WekWeekBean> result = new ArrayList<>();
|
|
QueryWrapper<WekRecord> queryWrapper = new QueryWrapper<>();
|
queryWrapper.lambda().eq(WekRecord::getYear, year).eq(WekRecord::getUser, username).and(j -> j.in(WekRecord::getWeek, week));
|
queryWrapper.lambda().orderByAsc(WekRecord::getCreateTime);
|
List<WekRecord> list = this.list(queryWrapper);
|
//没有数据则返回空白数据
|
if (list.isEmpty()) {
|
return createEmptyData(year, week,username);
|
}
|
|
|
//根据周和数据类型分类
|
Map<Integer, Map<Integer, List<WekRecord>>> collect = list.stream().collect(Collectors.groupingBy(t -> t.getWeek(), Collectors.groupingBy(t -> t.getType())));
|
|
for (Map.Entry<Integer, Map<Integer, List<WekRecord>>> entry : collect.entrySet()) {
|
Map<Integer, List<WekRecord>> typeMap = entry.getValue();
|
WekWeekBean weekBean = new WekWeekBean();
|
weekBean.setWeek(entry.getKey());
|
weekBean.setStartDateStr1(DateUtils.weekToDayStartStr(year, entry.getKey()));
|
weekBean.setEndDateStr1(DateUtils.weekToDayEndStr(year, entry.getKey()));
|
String tws = DateUtils.weekToDayEndStr(year, entry.getKey(), "yyyy-MM-dd");
|
weekBean.setWeekInMonth(DateUtils.getWeekInMonth(tws,2));
|
weekBean.setStartDateStr2(DateUtils.weekToDayStartStr(year, entry.getKey() + 1));
|
weekBean.setEndDateStr2(DateUtils.weekToDayEndStr(year, entry.getKey() + 1));
|
weekBean.setShow(true);
|
weekBean.setUsername(username);
|
weekBean.setShowDetail(true);
|
List<WekTypeBean> typeList = new ArrayList<>();
|
for (int i = 0; i < 4; i++) {
|
WekTypeBean typeBean = new WekTypeBean();
|
typeBean.setWeek(entry.getKey());
|
typeBean.setType(i);
|
configTypeName(entry.getKey(), typeBean);
|
if (typeMap.containsKey(i)) {
|
typeBean.setWekList(typeMap.get(i));
|
} else {
|
List<WekRecord> wekRecords = new ArrayList<>();
|
typeBean.setWekList(wekRecords);
|
}
|
typeList.add(typeBean);
|
}
|
|
weekBean.setTypeList(typeList);
|
weekBean.setUsername(username);
|
weekBean.setYear(year);
|
result.add(weekBean);
|
}
|
|
return result;
|
}
|
|
@Override
|
public List<WekWeekBean> queryDepartUserWeeklyList(String orgCode, int page) {
|
List<WekWeekBean> result = new ArrayList<>();
|
//查询部门下用户
|
List<String> departUsers = wekRecordMapper.queryDepartUsers(orgCode);
|
|
if (departUsers == null || departUsers.size() < 1) {
|
return result;
|
}
|
WekRecord mapParams = new WekRecord();
|
|
//先查询数据的年 周
|
List<HashMap<String, Object>> hashMaps = wekRecordMapper.queryYearWeekGroup(mapParams);
|
|
//页码大于总数据时
|
if (page > hashMaps.size()) {
|
return result;
|
}
|
HashMap<String, Object> stringObjectHashMap = hashMaps.get(page - 1);
|
int curYear = (int) stringObjectHashMap.get("year");
|
int curWeek = (int) stringObjectHashMap.get("week");
|
//拼接查询条件
|
QueryWrapper<WekRecord> queryWrapper = new QueryWrapper<>();
|
queryWrapper.in("user", departUsers).in("year", curYear).in("week", curWeek).orderByDesc("user").orderByDesc("year").orderByDesc("week").orderByAsc("type");
|
queryWrapper.lambda().orderByAsc(WekRecord::getCreateTime);
|
//查询数据
|
List<WekRecord> list = wekRecordMapper.selectList(queryWrapper);
|
//按照 用户-周-数据类型 分类数据
|
Map<String, Map<Integer, Map<Integer, List<WekRecord>>>> collect = list.stream().collect(Collectors.groupingBy(t -> t.getUser(), Collectors.groupingBy(t -> t.getWeek(), Collectors.groupingBy(t -> t.getType()))));
|
|
for (Map.Entry<String, Map<Integer, Map<Integer, List<WekRecord>>>> userEntry : collect.entrySet()) {
|
Map<Integer, Map<Integer, List<WekRecord>>> weekMap = userEntry.getValue();
|
for (Map.Entry<Integer, Map<Integer, List<WekRecord>>> entry : weekMap.entrySet()) {
|
Map<Integer, List<WekRecord>> typeMap = entry.getValue();
|
WekWeekBean weekBean = new WekWeekBean();
|
weekBean.setWeek(entry.getKey());
|
weekBean.setStartDateStr1(DateUtils.weekToDayStartStr(entry.getKey()));
|
weekBean.setEndDateStr1(DateUtils.weekToDayEndStr(entry.getKey()));
|
weekBean.setStartDateStr2(DateUtils.weekToDayStartStr(entry.getKey() + 1));
|
weekBean.setEndDateStr2(DateUtils.weekToDayEndStr(entry.getKey() + 1));
|
weekBean.setShow(true);
|
List<WekTypeBean> typeList = new ArrayList<>();
|
for (int i = 0; i < 4; i++) {
|
WekTypeBean typeBean = new WekTypeBean();
|
typeBean.setWeek(entry.getKey());
|
typeBean.setType(i);
|
configTypeName(entry.getKey(), typeBean);
|
if (typeMap.containsKey(i)) {
|
typeBean.setWekList(typeMap.get(i));
|
} else {
|
List<WekRecord> wekRecords = new ArrayList<>();
|
typeBean.setWekList(wekRecords);
|
}
|
typeList.add(typeBean);
|
}
|
|
weekBean.setTypeList(typeList);
|
weekBean.setYear(curYear);
|
weekBean.setUsername(userEntry.getKey());
|
result.add(weekBean);
|
}
|
}
|
|
//姓名升序
|
Comparator nameCom = Comparator.comparing(
|
WekWeekBean::getUsername);
|
//week 降序
|
Comparator weekCom = Comparator.comparingInt(
|
WekWeekBean::getWeek).reversed();
|
result.sort(nameCom.thenComparing(weekCom));
|
|
return result;
|
}
|
|
|
@Override
|
public List<WekWeekBean> queryJuniorBatchWeekly(String usernames, int page) {
|
List<WekWeekBean> result = new ArrayList<>();
|
String[] split = usernames.split(",");
|
//查询部门下用户
|
List<String> departUsers = Arrays.asList(split);
|
|
if (departUsers == null || departUsers.size() < 1) {
|
return result;
|
}
|
WekRecord mapParams = new WekRecord();
|
|
//先查询数据的年 周
|
List<HashMap<String, Object>> hashMaps = wekRecordMapper.queryYearWeekGroup(mapParams);
|
|
//页码大于总数据时
|
if (page > hashMaps.size()) {
|
return result;
|
}
|
HashMap<String, Object> stringObjectHashMap = hashMaps.get(page - 1);
|
int curYear = (int) stringObjectHashMap.get("year");
|
int curWeek = (int) stringObjectHashMap.get("week");
|
//拼接查询条件
|
QueryWrapper<WekRecord> queryWrapper = new QueryWrapper<>();
|
queryWrapper.in("user", departUsers).in("year", curYear).in("week", curWeek).orderByDesc("user").orderByDesc("year").orderByDesc("week").orderByAsc("type");
|
//查询数据
|
List<WekRecord> list = wekRecordMapper.selectList(queryWrapper);
|
//按照 用户-周-数据类型 分类数据
|
Map<String, Map<Integer, Map<Integer, List<WekRecord>>>> collect = list.stream().collect(Collectors.groupingBy(t -> t.getUser(), Collectors.groupingBy(t -> t.getWeek(), Collectors.groupingBy(t -> t.getType()))));
|
|
for (Map.Entry<String, Map<Integer, Map<Integer, List<WekRecord>>>> userEntry : collect.entrySet()) {
|
Map<Integer, Map<Integer, List<WekRecord>>> weekMap = userEntry.getValue();
|
for (Map.Entry<Integer, Map<Integer, List<WekRecord>>> entry : weekMap.entrySet()) {
|
Map<Integer, List<WekRecord>> typeMap = entry.getValue();
|
WekWeekBean weekBean = new WekWeekBean();
|
weekBean.setWeek(entry.getKey());
|
weekBean.setStartDateStr1(DateUtils.weekToDayStartStr(entry.getKey()));
|
weekBean.setEndDateStr1(DateUtils.weekToDayEndStr(entry.getKey()));
|
weekBean.setStartDateStr2(DateUtils.weekToDayStartStr(entry.getKey() + 1));
|
weekBean.setEndDateStr2(DateUtils.weekToDayEndStr(entry.getKey() + 1));
|
weekBean.setShow(true);
|
List<WekTypeBean> typeList = new ArrayList<>();
|
for (int i = 0; i < 4; i++) {
|
WekTypeBean typeBean = new WekTypeBean();
|
typeBean.setWeek(entry.getKey());
|
typeBean.setType(i);
|
configTypeName(entry.getKey(), typeBean);
|
if (typeMap.containsKey(i)) {
|
typeBean.setWekList(typeMap.get(i));
|
} else {
|
List<WekRecord> wekRecords = new ArrayList<>();
|
typeBean.setWekList(wekRecords);
|
}
|
typeList.add(typeBean);
|
}
|
|
weekBean.setTypeList(typeList);
|
weekBean.setYear(curYear);
|
weekBean.setUsername(userEntry.getKey());
|
result.add(weekBean);
|
}
|
}
|
|
//姓名升序
|
Comparator nameCom = Comparator.comparing(
|
WekWeekBean::getUsername);
|
//week 降序
|
Comparator weekCom = Comparator.comparingInt(
|
WekWeekBean::getWeek).reversed();
|
result.sort(nameCom.thenComparing(weekCom));
|
|
return result;
|
}
|
|
@Override
|
public List<ProjectTreeVo> projectTreeList(ProProject project) {
|
List<ProProject> proProjects = wekRecordMapper.queryProjectList(project);
|
ProjectTreeVo treeVo = new ProjectTreeVo();
|
Map<String, Object> slotMap = new HashMap<>();
|
slotMap.put("icon", "proGroup");
|
treeVo.setId("0");
|
treeVo.setTitle("项目列表");
|
treeVo.setValue("0");
|
treeVo.setType(1);
|
treeVo.setScopedSlots(slotMap);
|
|
List<ProjectTreeVo> result = new ArrayList<>();
|
List<ProjectTreeVo> subList = new ArrayList<>();
|
for (int i = 0; i < proProjects.size(); i++) {
|
ProProject proProject = proProjects.get(i);
|
ProjectTreeVo vo = new ProjectTreeVo(proProject);
|
Map<String, Object> slot = new HashMap<>();
|
slot.put("icon", "proItem");
|
vo.setLeaf(true);
|
vo.setType(2);
|
vo.setScopedSlots(slot);
|
subList.add(vo);
|
}
|
treeVo.setChildren(subList);
|
result.add(treeVo);
|
|
return result;
|
}
|
|
@Override
|
public List<WekProject> queryProjectWeekly(String xm, int page) {
|
List<WekProject> result = new ArrayList<>();
|
|
WekRecord mapParams = new WekRecord();
|
if (!StringUtils.isEmpty(xm)) {
|
mapParams.setXm(xm);
|
}
|
//先查询数据的年 周
|
List<HashMap<String, Object>> hashMaps = wekRecordMapper.queryYearWeekGroup(mapParams);
|
|
//页码大于总数据时
|
if (page > hashMaps.size()) {
|
return result;
|
}
|
HashMap<String, Object> stringObjectHashMap = hashMaps.get(page - 1);
|
int curYear = (int) stringObjectHashMap.get("year");
|
int curWeek = (int) stringObjectHashMap.get("week");
|
|
|
QueryWrapper<WekRecord> queryWrapper = new QueryWrapper<>();
|
queryWrapper.lambda().eq(WekRecord::getYear, curYear).and(j -> j.in(WekRecord::getWeek, curWeek));
|
//条件查询
|
if (!StringUtils.isEmpty(xm)) {
|
queryWrapper.lambda().eq(WekRecord::getXm, xm);
|
}
|
queryWrapper.lambda().orderByAsc(WekRecord::getUser);
|
//只查询0-本周总结
|
queryWrapper.lambda().eq(WekRecord::getType, 0);
|
List<WekRecord> list = wekRecordMapper.selectList(queryWrapper);
|
|
//根据周分类
|
Map<Integer, List<WekRecord>> collect = list.stream().collect(Collectors.groupingBy(t -> t.getWeek()));
|
|
for (Map.Entry<Integer, List<WekRecord>> entry : collect.entrySet()) {
|
List<WekRecord> value = entry.getValue();
|
WekProject pro = new WekProject();
|
Map<String, String> colorMap = new HashMap<>();
|
pro.setWeek(entry.getKey());
|
pro.setYear(curYear);
|
pro.setStartDateStr1(DateUtils.weekToDayStartStr(entry.getKey()));
|
pro.setEndDateStr1(DateUtils.weekToDayEndStr(entry.getKey()));
|
pro.setWekRecordList(value);
|
pro.setXmName(value.get(0).getXmName());
|
pro.setShow(true);
|
|
//根据项目内成员生成颜色
|
for (int i = 0; i < value.size(); i++) {
|
WekRecord record = value.get(i);
|
if (!colorMap.containsKey(record.getUser()))
|
colorMap.put(record.getUser(), HTMLUtils.getColor(colorMap.size()));
|
}
|
pro.setColorMap(colorMap);
|
result.add(pro);
|
|
}
|
return result;
|
|
}
|
|
@Override
|
public List<WekProject> queryAllProjectWeekly(int page) {
|
|
List<WekProject> result = new ArrayList<>();
|
WekRecord mapParams = new WekRecord();
|
//先查询数据的年 周
|
List<HashMap<String, Object>> hashMaps = wekRecordMapper.queryAllXmYearWeekGroup(mapParams);
|
|
//页码大于总数据时
|
if (page > hashMaps.size()) {
|
return result;
|
}
|
HashMap<String, Object> stringObjectHashMap = hashMaps.get(page - 1);
|
int curYear = (int) stringObjectHashMap.get("year");
|
int curWeek = (int) stringObjectHashMap.get("week");
|
|
QueryWrapper<WekRecord> queryWrapper = new QueryWrapper<>();
|
queryWrapper.in("year", curYear).in("week", curWeek).in("type", 0).isNotNull("xm").orderByDesc("year").orderByDesc("week").orderByAsc("user");
|
//查询数据
|
List<WekRecord> list = wekRecordMapper.selectList(queryWrapper);
|
//按照 项目-周 分类数据
|
Map<String, Map<Integer, List<WekRecord>>> collect = list.stream().collect(Collectors.groupingBy(t -> t.getXm(), Collectors.groupingBy(t -> t.getWeek())));
|
|
for (Map.Entry<String, Map<Integer, List<WekRecord>>> project : collect.entrySet()) {
|
String xm = project.getKey();
|
for (Map.Entry<Integer, List<WekRecord>> entry : project.getValue().entrySet()) {
|
List<WekRecord> value = entry.getValue();
|
WekProject pro = new WekProject();
|
Map<String, String> colorMap = new HashMap<>();
|
pro.setWeek(entry.getKey());
|
pro.setYear(curYear);
|
pro.setStartDateStr1(DateUtils.weekToDayStartStr(entry.getKey()));
|
pro.setEndDateStr1(DateUtils.weekToDayEndStr(entry.getKey()));
|
pro.setWekRecordList(value);
|
pro.setXmName(value.get(0).getXmName());
|
pro.setShow(true);
|
|
//根据项目内成员生成颜色
|
for (int i = 0; i < value.size(); i++) {
|
WekRecord record = value.get(i);
|
if (!colorMap.containsKey(record.getUser()))
|
colorMap.put(record.getUser(), HTMLUtils.getColor(colorMap.size()));
|
}
|
pro.setColorMap(colorMap);
|
result.add(pro);
|
}
|
}
|
//项目名升序
|
Comparator nameCom = Comparator.comparing(
|
WekProject::getXmName);
|
//week 降序
|
Comparator weekCom = Comparator.comparingInt(
|
WekProject::getWeek).reversed();
|
result.sort(nameCom.thenComparing(weekCom));
|
return result;
|
}
|
|
@Override
|
public Result<List<Map<String, Object>>> statisticsList(WekRecord wekRecord) {
|
Result<List<Map<String, Object>>> result = new Result<>();
|
int SUB_TYPE_1 = 1;//项目相关工作
|
int SUB_TYPE_2 = 2;//日常事务工作
|
|
//查询参数
|
Map<String, Object> param = new HashMap<>();
|
param.put("xm", wekRecord.getXm()); //项目名称
|
param.put("user", wekRecord.getUser());//用户
|
//计算日期的周
|
if (wekRecord.getKsrq() != null) {
|
Integer sno = DateUtils.getWeekNoByDate(wekRecord.getKsrq());
|
int year = DateUtils.getYear(wekRecord.getKsrq());
|
param.put("syear", year);//查询开始年份
|
param.put("sweek", sno);//查询开始星期号
|
}
|
if (wekRecord.getJsrq() != null) {
|
Integer eno = DateUtils.getWeekNoByDate(wekRecord.getJsrq());
|
int year = DateUtils.getYear(wekRecord.getJsrq());
|
param.put("eyear", year);//查询结束年份
|
param.put("eweek", eno);//查询结束星期号
|
}
|
|
|
//查询数据包括type 0-本周总结 和 1-本周计划外工作
|
//0对数据进行分组,通过subtype进行分组 subtype 1-项目相关工作 2-日常事务工作(需统计type 0-本周总结 和 1-本周计划外工作,只区分项目相关和日常事务)
|
List<WekRecord> list = wekRecordMapper.statisticsList(param);
|
//测试 TODO 删除
|
// list = list.stream().filter(i -> i.getId().intValue() <= 150).collect(Collectors.toList());
|
|
//统计有周报记录的所有成员(表格的列)
|
List<Map<String, Object>> userList = new ArrayList<>();
|
list.removeIf(item -> item.getUser() == null);
|
Map<String, List<WekRecord>> userMaps = list.stream().collect(Collectors.groupingBy(t -> t.getUser()));
|
for (Map.Entry<String, List<WekRecord>> user : userMaps.entrySet()) {
|
Map<String, Object> map = new HashMap<>();
|
map.put("name", user.getKey());
|
userList.add(map);
|
|
}
|
//合计
|
Map<String, Object> hjMap = new HashMap<>();
|
//纵向合计(个人总工时合计)
|
hjMap.put("xm", "hj");
|
hjMap.put("xmName", "合计");
|
|
//1.1. 过滤subtype 1-项目相关工作数据
|
list.removeIf(item -> item.getSubType() == null);
|
List<WekRecord> proWeeklyList = list.stream().filter(item -> item.getSubType() == SUB_TYPE_1).collect(Collectors.toList());
|
proWeeklyList.removeIf(item -> item.getXm() == null);
|
|
//1.2.统计项目-成员的工时(表格每一行数据)
|
List<Map<String, Object>> proResultList = new ArrayList<>();
|
Map<String, Map<String, List<WekRecord>>> proCollect = proWeeklyList.stream().collect(Collectors.groupingBy(t -> t.getXm(), Collectors.groupingBy(t -> t.getUser())));
|
for (Map.Entry<String, Map<String, List<WekRecord>>> project : proCollect.entrySet()) {
|
Map<String, Object> item = new HashMap<>();
|
String key = project.getKey();
|
Map<String, List<WekRecord>> userMap = project.getValue();
|
//项目
|
item.put("xm", key);
|
|
for (Map.Entry<String, List<WekRecord>> user : userMap.entrySet()) {
|
//统计项目内个人的工时
|
item.put(user.getKey(), user.getValue().stream().filter(wek -> wek.getGs() != null).mapToDouble(WekRecord::getGs).sum());
|
if (user.getValue() != null && user.getValue().size() > 0)
|
item.put("xmName", user.getValue().get(0).getXmName());
|
|
Double cur = (Double) item.get(user.getKey());
|
//统计总工时
|
if (hjMap.containsKey(user.getKey())) {
|
Double total = (Double) hjMap.get(user.getKey());
|
hjMap.put(user.getKey(), total + cur);
|
} else {
|
hjMap.put(user.getKey(), cur);
|
}
|
}
|
proResultList.add(item);
|
}
|
|
//2.1 过滤subtype 2-日常事务工作
|
List<WekRecord> extWeeklyList = list.stream().filter(item -> item.getSubType() == SUB_TYPE_2).collect(Collectors.toList());
|
extWeeklyList.removeIf(item -> item.getExt() == null);
|
//2.2.统计日常事务-成员的工时(表格每一行数据)
|
List<Map<String, Object>> extResultList = new ArrayList<>();
|
Map<Integer, Map<String, List<WekRecord>>> extCollect = extWeeklyList.stream().collect(Collectors.groupingBy(t -> t.getExt(), Collectors.groupingBy(t -> t.getUser())));
|
for (Map.Entry<Integer, Map<String, List<WekRecord>>> ext : extCollect.entrySet()) {
|
Map<String, Object> item = new HashMap<>();
|
Integer key = ext.getKey();
|
Map<String, List<WekRecord>> userMap = ext.getValue();
|
//日常事务id //TODO 为统一前端数据,需要把键设置与项目数据一致
|
//item.put("ext",key);
|
item.put("xm", key);
|
|
for (Map.Entry<String, List<WekRecord>> user : userMap.entrySet()) {
|
//统计日常事务内个人的工时
|
item.put(user.getKey(), user.getValue().stream().filter(wek -> wek.getGs() != null).mapToDouble(WekRecord::getGs).sum());
|
if (user.getValue() != null && user.getValue().size() > 0)
|
//TODO 为统一前端数据,需要把键设置与项目数据一致
|
item.put("xmName", user.getValue().get(0).getExtName());
|
|
Double cur = (Double) item.get(user.getKey());
|
//统计总工时
|
if (hjMap.containsKey(user.getKey())) {
|
Double total = (Double) hjMap.get(user.getKey());
|
hjMap.put(user.getKey(), total + cur);
|
} else {
|
hjMap.put(user.getKey(), cur);
|
}
|
}
|
extResultList.add(item);
|
}
|
|
List<Map<String, Object>> resultList = new ArrayList<>();
|
|
resultList.add(hjMap);
|
resultList.addAll(extResultList);
|
resultList.addAll(proResultList);
|
//计算合计工时
|
for (int i = 0; i < resultList.size(); i++) {
|
Map<String, Object> map = resultList.get(i);
|
Double hj = 0.0;
|
for (Map.Entry<String, Object> item : map.entrySet()) {
|
if (item.getValue() instanceof Double) {
|
hj += (Double) item.getValue();
|
}
|
}
|
//横向合计(项目总工时合计)
|
map.put("hj", hj);
|
}
|
|
result.setResult(resultList);
|
result.setResultExt(userList);
|
|
return result;
|
}
|
|
@Override
|
public Result<List<Map<String, Object>>> statisticsYearList(WekRecord wekRecord) {
|
List<ProProject> proProjects = wekRecordMapper.queryProjectList(null);
|
Map<String, List<ProProject>> xmMaps = proProjects.stream().collect(Collectors.groupingBy(t -> t.getId()));
|
Result<List<Map<String, Object>>> result = new Result<>();
|
//1.生成title
|
Map<String, Object> root = createStatisticsYearTitle();
|
List<Map<String, Object>> statisticsYearTitle = (List<Map<String, Object>>) root.get("colmuns");
|
Map<Integer, String> configMap = (Map<Integer, String>) root.get("config");
|
|
//2.生成数据
|
List<Map<String, Object>> record = new ArrayList<>();
|
int SUB_TYPE_1 = 1;//项目相关工作
|
int SUB_TYPE_2 = 2;//日常事务工作
|
int curYear = DateUtils.getCurYear();
|
|
QueryWrapper<WekRecord> queryWrapper = new QueryWrapper<>();
|
//查询数据包括type 0-本周总结 和 1-本周计划外工作
|
queryWrapper.lambda().eq(WekRecord::getYear, curYear).in(WekRecord::getType, Arrays.asList(0, 1));
|
if (!StringUtils.isEmpty(wekRecord.getXm())) {
|
queryWrapper.lambda().in(WekRecord::getXm, Arrays.asList(wekRecord.getXm().split(",")));
|
}
|
List<WekRecord> list = wekRecordMapper.selectList(queryWrapper);
|
//2.1统计项目相关数据
|
list.removeIf(item -> item.getSubType() == null);
|
List<WekRecord> proWeeklyList = list.stream().filter(item -> item.getSubType() == SUB_TYPE_1).collect(Collectors.toList());
|
proWeeklyList.removeIf(item -> item.getXm() == null);
|
List<Map<String, Object>> proResultList = new ArrayList<>();
|
Map<String, Map<Integer, List<WekRecord>>> proCollect = proWeeklyList.stream().collect(Collectors.groupingBy(t -> t.getXm(), Collectors.groupingBy(t -> t.getWeek())));
|
for (Map.Entry<String, Map<Integer, List<WekRecord>>> project : proCollect.entrySet()) {
|
Map<String, Object> item = new HashMap<>();
|
String key = project.getKey();
|
Map<Integer, List<WekRecord>> weekMap = project.getValue();
|
//项目
|
item.put("xm", key);
|
//组装数据列、统计周、季度工时
|
statisWeeklyGs(configMap, weekMap, item, SUB_TYPE_1);
|
|
proResultList.add(item);
|
}
|
|
//2.2 过滤subtype 2-日常事务工作
|
List<WekRecord> extWeeklyList = list.stream().filter(item -> item.getSubType() == SUB_TYPE_2).collect(Collectors.toList());
|
extWeeklyList.removeIf(item -> item.getExt() == null);
|
List<Map<String, Object>> extResultList = new ArrayList<>();
|
Map<Integer, Map<Integer, List<WekRecord>>> extCollect = extWeeklyList.stream().collect(Collectors.groupingBy(t -> t.getExt(), Collectors.groupingBy(t -> t.getWeek())));
|
for (Map.Entry<Integer, Map<Integer, List<WekRecord>>> ext : extCollect.entrySet()) {
|
Map<String, Object> item = new HashMap<>();
|
Integer key = ext.getKey();
|
Map<Integer, List<WekRecord>> weekMap = ext.getValue();
|
//日常事务id //TODO 为统一前端数据,需要把键设置与项目数据一致
|
//item.put("ext",key);
|
item.put("xm", key);
|
|
//组装数据列、统计周、季度工时
|
statisWeeklyGs(configMap, weekMap, item, SUB_TYPE_2);
|
extResultList.add(item);
|
}
|
List<Map<String, Object>> resultList = new ArrayList<>();
|
|
extResultList.addAll(proResultList);
|
|
//添加一条合计数据
|
Map<String, Object> hjMap = new HashMap<>();
|
hjMap.put("xm", 0);
|
hjMap.put("xmName", "总工时");
|
//统计总工时
|
double total = extResultList.stream().mapToDouble(t -> Double.parseDouble(t.get("total").toString())).sum();
|
hjMap.put("total", total);
|
hjMap.put("prop", "100%");
|
for (int i = 0; i < extResultList.size(); i++) {
|
if (extResultList.size() < 1) continue;
|
Map<String, Object> map = extResultList.get(i);
|
if (!map.containsKey("total")) continue;
|
//项目工时
|
double xmGs = Double.parseDouble(map.get("total").toString());
|
if (xmGs <= 0) continue;
|
//计算项目工时占比
|
NumberFormat nf = NumberFormat.getPercentInstance();
|
nf.setMinimumFractionDigits(2);
|
String res = nf.format((float) xmGs / (float) total);
|
map.put("prop", res);
|
|
//获取项目信息
|
List<ProProject> xm = xmMaps.get(map.get("xm"));
|
if (xm != null && xm.size() > 0) {
|
map.put("xmfzr", xm.get(0).getXmfzr());
|
map.put("xmlx", xm.get(0).getXmlx());
|
map.put("year", DateUtils.date2Str(xm.get(0).getKsrq(), new SimpleDateFormat("yyyy")));
|
}
|
|
|
//统计合计值
|
for (Map.Entry<String, Object> entry : map.entrySet()) {
|
String key = entry.getKey();
|
if (!key.startsWith("m") && !key.startsWith("s")) continue;
|
Object value = entry.getValue();
|
if (value instanceof Number) {
|
if (!hjMap.containsKey(key)) {
|
hjMap.put(key, value);
|
} else {
|
Double o = (Double) hjMap.get(key);
|
Double v = (Double) value;
|
hjMap.put(key, o + v);
|
}
|
}
|
|
|
}
|
|
|
}
|
|
resultList.add(hjMap);
|
resultList.addAll(extResultList);
|
|
result.setResultExt(statisticsYearTitle);
|
result.setResult(resultList);
|
|
return result;
|
}
|
|
@Override
|
public Map<String, Object> customExportWeekly(WekRecord wekRecord) {
|
Map<String, Object> res = new HashMap<>();
|
int SUB_TYPE_1 = 1;//项目相关工作
|
int SUB_TYPE_2 = 2;//日常事务工作
|
|
//查询参数
|
Map<String, Object> param = new HashMap<>();
|
param.put("xm", wekRecord.getXm()); //项目名称
|
param.put("user", wekRecord.getUser());//用户
|
//计算日期的周
|
if (wekRecord.getKsrq() != null) {
|
Integer sno = DateUtils.getWeekNoByDate(wekRecord.getKsrq());
|
int year = DateUtils.getYear(wekRecord.getKsrq());
|
param.put("syear", year);//查询开始年份
|
param.put("sweek", sno);//查询开始星期号
|
}
|
if (wekRecord.getJsrq() != null) {
|
Integer eno = DateUtils.getWeekNoByDate(wekRecord.getJsrq());
|
int year = DateUtils.getYear(wekRecord.getJsrq());
|
param.put("eyear", year);//查询结束年份
|
param.put("eweek", eno);//查询结束星期号
|
}
|
|
|
//查询所有项目
|
List<ProProject> proProjects = wekRecordMapper.queryProjectList(null);
|
Map<String, ProProject> allproMap = proProjects.stream().collect(Collectors.toMap(ProProject::getId, item -> item));
|
//查询所有用户
|
Object o = redisUtil.get(CacheConstant.SYS_USER_ALL_CACHE);
|
Map<String, String> alluserMap = new HashMap<>();
|
if (o != null) {
|
alluserMap = (Map) JSON.parse(o.toString());
|
}
|
|
List<WekRecord> wekList = wekRecordMapper.statisticsList(param);
|
//根据部门过滤
|
List<WekRecord> list = departFilter(wekRecord, wekList);
|
|
|
//统计有周报记录的所有成员(表格的列)
|
List<Map<String, Object>> userList = new ArrayList<>();
|
list.removeIf(item -> item.getUser() == null);
|
Map<String, List<WekRecord>> userMaps = list.stream().collect(Collectors.groupingBy(t -> t.getUser()));
|
for (Map.Entry<String, List<WekRecord>> user : userMaps.entrySet()) {
|
Map<String, Object> map = new HashMap<>();
|
map.put("name", alluserMap.get(user.getKey()));
|
map.put("column", "{pro." + user.getKey() + "}");
|
map.put("key", user.getKey());
|
userList.add(map);
|
}
|
|
Map<String, Object> map = new HashMap<>();
|
map.put("name", "合计");
|
map.put("column", "{pro.hj}");
|
map.put("key", "hj");
|
userList.add(map);
|
|
|
//1.1. 过滤subtype 1-项目相关工作数据
|
list.removeIf(item -> item.getSubType() == null);
|
List<WekRecord> proWeeklyList = list.stream().filter(item -> item.getSubType() == SUB_TYPE_1).collect(Collectors.toList());
|
proWeeklyList.removeIf(item -> item.getXm() == null || item.getUser() == null);
|
|
//1.2.统计项目-成员的工时(表格每一行数据) 项目相关数据
|
List<Map<String, Object>> proResultList = new ArrayList<>();
|
Map<String, Map<String, List<WekRecord>>> proCollect = proWeeklyList.stream().collect(Collectors.groupingBy(t -> t.getXm(), Collectors.groupingBy(t -> t.getUser())));
|
|
proCollect.forEach((String xm, Map<String, List<WekRecord>> xmWekMap) -> {
|
Map<String, Object> item = new HashMap<>();
|
ProProject proProject = allproMap.get(xm);
|
item.put("xmmc", proProject.getXmmc());
|
item.put("xmbh", proProject.getXmbh());
|
//一个项目的合计工时
|
AtomicReference<Double> hj = new AtomicReference<>(0.0);
|
xmWekMap.forEach((String user, List<WekRecord> userWekList) -> {
|
double sum = userWekList.stream().filter(i -> i.getGs() != null).mapToDouble(i -> i.getGs()).sum();
|
item.put(user, sum);
|
hj.updateAndGet(v -> new Double((double) (v + sum)));
|
});
|
item.put("hj", hj.get());
|
userList.forEach(i -> {
|
String userkey = i.get("key").toString();
|
if (!item.containsKey(userkey)) {
|
item.put(userkey, 0.0);
|
}
|
});
|
|
proResultList.add(item);
|
});
|
|
List<WekRecord> extWeeklyList = list.stream().filter(item -> item.getSubType() == SUB_TYPE_2).collect(Collectors.toList());
|
extWeeklyList.removeIf(item -> item.getExtName() == null || item.getUser() == null);
|
|
//1.3 统计其他-成员的工时(表格每一行数据) 其他相关数据
|
List<Map<String, Object>> extResultList = new ArrayList<>();
|
Map<String, Map<String, List<WekRecord>>> extCollect = extWeeklyList.stream().collect(Collectors.groupingBy(t -> t.getExtName(), Collectors.groupingBy(t -> t.getUser())));
|
|
extCollect.forEach((String extName, Map<String, List<WekRecord>> xmWekMap) -> {
|
Map<String, Object> item = new HashMap<>();
|
item.put("xmmc", extName);
|
item.put("xmbh", "");
|
//其他相关数据的合计工时
|
AtomicReference<Double> hj = new AtomicReference<>(0.0);
|
xmWekMap.forEach((String user, List<WekRecord> userWekList) -> {
|
double sum = userWekList.stream().filter(i -> i.getGs() != null).mapToDouble(i -> i.getGs()).sum();
|
item.put(user, sum);
|
hj.updateAndGet(v -> new Double((double) (v + sum)));
|
});
|
item.put("hj", hj.get());
|
userList.forEach(i -> {
|
String userkey = i.get("key").toString();
|
if (!item.containsKey(userkey)) {
|
item.put(userkey, 0.0);
|
}
|
});
|
|
extResultList.add(item);
|
});
|
|
extResultList.addAll(proResultList);
|
//列 合计
|
Map<String, Object> item = new HashMap<>();
|
item.put("xmmc", "合计");
|
item.put("xmbh", "");
|
userList.forEach(i -> {
|
String col = i.get("key").toString();
|
Double sum = extResultList.stream().mapToDouble(j -> (Double) j.get(col)).sum();
|
item.put(col, sum.intValue());
|
});
|
List<Map<String, Object>> resultList = new ArrayList<>();
|
resultList.add(item);
|
resultList.addAll(extResultList);
|
|
String ks = DateUtils.getWeekInMonth(wekRecord.getKsrq());
|
// int smonth = DateUtils.getMonth(wekRecord.getKsrq());
|
// int syear = DateUtils.getYear(wekRecord.getKsrq());
|
|
String js = DateUtils.getWeekInMonth(wekRecord.getJsrq());
|
// int emonth = DateUtils.getMonth(wekRecord.getJsrq());
|
// int eyear = DateUtils.getYear(wekRecord.getJsrq());
|
|
String sks = DateUtils.date2Str(wekRecord.getKsrq(), DateUtils.date_sdf.get());
|
String sjs = DateUtils.date2Str(wekRecord.getJsrq(), DateUtils.date_sdf.get());
|
|
res.put("title", ks + " ~ " + js + "("+sks +" - "+ sjs+")");
|
res.put("users", userList);
|
res.put("data", resultList);
|
|
if(wekRecord.getDetailFlag()==1){
|
List<Map<String, Object>> userWeeklys = createUserWeeklys(list, userList);
|
res.put("usersweeklys", userWeeklys);
|
}
|
|
|
return res;
|
|
}
|
|
/**
|
* 周报数据按照、用户、年、周分组
|
*
|
* @param list 周报记录
|
* @param userList 用户列表
|
*/
|
private List<Map<String, Object>> createUserWeeklys(List<WekRecord> list, List<Map<String, Object>> userList) {
|
List<String> users = userList.stream().map(i -> {
|
return i.get("key").toString();
|
}).collect(Collectors.toList());
|
//查询所有用户信息
|
List<HashMap<String, Object>> userInfoList = wekRecordMapper.queryUsersInfoByNames(users);
|
Map<String, HashMap<String, Object>> userinfos = userInfoList.stream()
|
.collect(Collectors.toMap(item -> item.get("username").toString(), item -> item, (v1, v2) -> {
|
return v1;
|
}));
|
|
List<Map<String, Object>> usersweekly = new ArrayList<>();
|
list.removeIf(i -> i.getYear() == null || i.getWeek() == null);
|
Map<String, Map<Integer, Map<Integer, List<WekRecord>>>> collect = list.stream().collect(Collectors.groupingBy(i -> i.getUser(), Collectors.groupingBy(t -> t.getYear(), Collectors.groupingBy(t -> t.getWeek()))));
|
collect.forEach((user, uWekMap) -> {
|
uWekMap.forEach((year, yWekMap) -> {
|
yWekMap.forEach((week, wList) -> {
|
Map<String, Object> userAweekly = createUserAweekly(user, year, week, wList, userinfos);
|
usersweekly.add(userAweekly);
|
|
});
|
});
|
});
|
return usersweekly;
|
}
|
|
/**
|
* @param user 用户usernmae
|
* @param year 周报所属年份
|
* @param week 周报所属周号
|
* @param wList 周报记录
|
* @param userinfos 用户信息
|
* @return
|
*/
|
private Map<String, Object> createUserAweekly(String user, Integer year, Integer week, List<WekRecord> wList, Map<String, HashMap<String, Object>> userinfos) {
|
Map<String, Object> res = new HashMap<>();
|
Map<String, Object> basisinfo = new HashMap<>();
|
String start = DateUtils.weekToDayStartStr(year, week, "yyyy-MM-dd");
|
String end = DateUtils.weekToFriDayEndStr(year, week, "yyyy-MM-dd");
|
String sheet = DateUtils.getWeekInMonth(end,2);
|
HashMap<String, Object> userMap = userinfos.get(user);
|
if (userinfos != null && userMap != null) {
|
basisinfo.put("departname", userMap.get("departname"));
|
basisinfo.put("post", userMap.get("post"));
|
basisinfo.put("realname", userMap.get("realname"));
|
}
|
|
basisinfo.put("start", start);
|
basisinfo.put("end", end);
|
basisinfo.put("sheet", basisinfo.containsKey("realname") ? basisinfo.get("realname") + "-" + sheet : user + "-" + sheet);
|
|
|
Map<Integer, List<WekRecord>> collect = wList.stream().collect(Collectors.groupingBy(i -> i.getType()));
|
//数据库周报类型
|
int[] types = {0, 1, 2, 3};
|
Map<String, Object> gsMap = new HashMap<>();
|
AtomicInteger dataIndex = new AtomicInteger(1);
|
collect.forEach((k, v) -> {
|
AtomicInteger index = new AtomicInteger(1);
|
List<Map<String, Object>> typeList = v.stream().map(i -> {
|
Map<String, Object> item = new HashMap<>();
|
if (k == types[0]) {
|
item.put("part", "本周工作汇报");
|
} else if (k == types[1]) {
|
item.put("part", "本周计划外工作");
|
} else if (k == types[2]) {
|
item.put("part", "下周工作计划");
|
} else if (k == types[3]) {
|
item.put("part", "需协调事务");
|
}
|
item.put("no", index.getAndIncrement());
|
if (i.getSubType() == 1) {
|
item.put("name", i.getXmName());
|
} else if (i.getSubType() == 2) {
|
item.put("name", i.getExtName());
|
}
|
item.put("wbs", i.getWbsName());
|
item.put("content", i.getGzms());
|
item.put("delivery", i.getXmDeliver());
|
item.put("hour", i.getGs());
|
|
Date createTime = i.getCreateTime();
|
|
int weekNo = DateUtils.getWeekNo(createTime);
|
item.put("mon", weekNo == 1 ? "√" : "");
|
item.put("tue", weekNo == 2 ? "√" : "");
|
item.put("wed", weekNo == 3 ? "√" : "");
|
item.put("thi", weekNo == 4 ? "√" : "");
|
item.put("fri", weekNo == 5 ? "√" : "");
|
return item;
|
}).filter(i -> i.containsKey("part")).collect(Collectors.toList());
|
|
res.put("data" + dataIndex, typeList);
|
double sum = v.stream().filter(i -> i.getGs() != null).mapToDouble(WekRecord::getGs).sum();
|
gsMap.put("zgs" + dataIndex, sum);
|
dataIndex.getAndIncrement();
|
});
|
res.put("zgs", gsMap);
|
res.put("basisinfo", basisinfo);
|
|
//导出周报考评信息
|
String eid = user + (year * 100 + week);
|
WekEvaluate wekEvaluate = wekEvaluateMapper.selectById(eid);
|
if(wekEvaluate!=null){
|
WekEvaluateBean bean = new WekEvaluateBean();
|
BeanUtils.copyProperties(wekEvaluate,bean);
|
if(bean.getZpDate()!=null){
|
String zpDate = DateUtils.date2Str(bean.getZpDate(), DateUtils.datetimeFormat.get());
|
bean.setZpDateStr(zpDate);
|
}
|
|
if(bean.getKpDate()!=null){
|
String kpDate = DateUtils.date2Str(bean.getKpDate(), DateUtils.datetimeFormat.get());
|
bean.setKpDateStr(kpDate);
|
}
|
Map<String, Object> evaMap = convertToMap(bean);
|
res.put("eva", evaMap);
|
}
|
|
|
return res;
|
|
}
|
|
|
@Override
|
public Map<String, Object> exportAweekly(WekRecord wekRecord) {
|
Map<String, Object> res = new HashMap<>();
|
QueryWrapper<WekRecord> queryWrapper = new QueryWrapper<>();
|
queryWrapper.lambda().eq(WekRecord::getYear, wekRecord.getYear());
|
queryWrapper.lambda().eq(WekRecord::getWeek, wekRecord.getWeek());
|
queryWrapper.lambda().eq(WekRecord::getUser, wekRecord.getUser());
|
|
if (wekRecord.getUser() == null || wekRecord.getYear() == null || wekRecord.getWeek() == null) {
|
return res;
|
}
|
//周报数据
|
List<WekRecord> list = wekRecordMapper.selectList(queryWrapper);
|
if (list == null || list.size() < 1) {
|
return res;
|
}
|
|
Map<Integer, List<WekRecord>> collect = list.stream().filter(i -> i.getSubType() != null && i.getType() != null).collect(Collectors.groupingBy(i -> i.getType()));
|
//数据库周报类型
|
int[] types = {0, 1, 2, 3};
|
Map<String, Object> gsMap = new HashMap<>();
|
AtomicInteger dataIndex = new AtomicInteger(1);
|
collect.forEach((k, v) -> {
|
AtomicInteger index = new AtomicInteger(1);
|
List<Map<String, Object>> typeList = v.stream().map(i -> {
|
Map<String, Object> item = new HashMap<>();
|
if (k == types[0]) {
|
item.put("part", "本周工作汇报");
|
} else if (k == types[1]) {
|
item.put("part", "本周计划外工作");
|
} else if (k == types[2]) {
|
item.put("part", "下周工作计划");
|
} else if (k == types[3]) {
|
item.put("part", "需协调事务");
|
}
|
item.put("no", index.getAndIncrement());
|
if (i.getSubType() == 1) {
|
item.put("name", i.getXmName());
|
} else if (i.getSubType() == 2) {
|
item.put("name", i.getExtName());
|
}
|
item.put("wbs", i.getWbsName());
|
item.put("content", i.getGzms());
|
item.put("delivery", i.getXmDeliver());
|
item.put("hour", i.getGs());
|
|
Date createTime = i.getCreateTime();
|
|
int weekNo = DateUtils.getWeekNo(createTime);
|
item.put("mon", weekNo == 1 ? "√" : "");
|
item.put("tue", weekNo == 2 ? "√" : "");
|
item.put("wed", weekNo == 3 ? "√" : "");
|
item.put("thi", weekNo == 4 ? "√" : "");
|
item.put("fri", weekNo == 5 ? "√" : "");
|
return item;
|
}).filter(i -> i.containsKey("part")).collect(Collectors.toList());
|
|
res.put("data" + dataIndex, typeList);
|
double sum = v.stream().filter(i -> i.getGs() != null).mapToDouble(WekRecord::getGs).sum();
|
gsMap.put("zgs" + dataIndex, sum);
|
dataIndex.getAndIncrement();
|
});
|
|
res.put("size", list.size());
|
res.put("zgs", gsMap);
|
|
//导出周报考评信息
|
String eid = wekRecord.getUser() + (wekRecord.getYear() * 100 + wekRecord.getWeek());
|
WekEvaluate wekEvaluate = wekEvaluateMapper.selectById(eid);
|
if(wekEvaluate!=null){
|
WekEvaluateBean bean = new WekEvaluateBean();
|
BeanUtils.copyProperties(wekEvaluate,bean);
|
if(bean.getZpDate()!=null){
|
String zpDate = DateUtils.date2Str(bean.getZpDate(), DateUtils.datetimeFormat.get());
|
bean.setZpDateStr(zpDate);
|
}
|
|
if(bean.getKpDate()!=null){
|
String kpDate = DateUtils.date2Str(bean.getKpDate(), DateUtils.datetimeFormat.get());
|
bean.setKpDateStr(kpDate);
|
}
|
Map<String, Object> evaMap = convertToMap(bean);
|
res.put("eva", evaMap);
|
}
|
|
return res;
|
}
|
|
public static Map<String, Object> convertToMap(Object entity) {
|
Map<String, Object> map = new HashMap<>();
|
|
Field[] fields = entity.getClass().getSuperclass().getDeclaredFields();
|
Field[] fields2 = entity.getClass().getDeclaredFields();
|
|
for (Field field : fields) {
|
field.setAccessible(true);
|
try {
|
Object value = field.get(entity);
|
map.put(field.getName(), value);
|
} catch (IllegalAccessException e) {
|
// 处理异常情况
|
e.printStackTrace();
|
}
|
}
|
|
for (Field field : fields2) {
|
field.setAccessible(true);
|
try {
|
Object value = field.get(entity);
|
map.put(field.getName(), value);
|
} catch (IllegalAccessException e) {
|
// 处理异常情况
|
e.printStackTrace();
|
}
|
}
|
|
return map;
|
}
|
|
@Override
|
public Map<String, Object> queryUserInfoByName(String user) {
|
List<HashMap<String, Object>> hashMaps = wekRecordMapper.queryUserInfoByName(user);
|
return hashMaps != null && hashMaps.size() > 0 ? hashMaps.get(0) : null;
|
}
|
|
@Override
|
public void calcWbsProgress(WekRecord wekRecord) {
|
String wbs = wekRecord.getWbs();
|
//没有wbs
|
if (StringUtils.isEmpty(wbs)) {
|
return;
|
}
|
//当前填写进度
|
Integer curJd = wekRecord.getJd();
|
if (curJd == null || curJd == 0) {
|
return;
|
}
|
QueryWrapper<WekRecord> wekRecordQueryWrapper = new QueryWrapper<>();
|
wekRecordQueryWrapper.lambda().eq(WekRecord::getWbs, wbs);
|
List<WekRecord> wekRecordList = wekRecordMapper.selectList(wekRecordQueryWrapper);
|
Map<String, List<WekRecord>> userWekMap = wekRecordList.stream().collect(Collectors.groupingBy(item -> item.getUser()));
|
Result<ProProjectLink> proLinkResult = projectClient.queryWbsId(wbs);
|
ProProjectLink result = proLinkResult.getResult();
|
if (result == null) return;
|
String zymc = result.getZymc();
|
if (StringUtils.isEmpty(zymc)) return;
|
String[] users = zymc.split(",");
|
int length = users.length;
|
|
//wbs 已完成
|
if (result.getWcjd() != null && result.getWcjd() == 1) {
|
return;
|
}
|
|
//如果当前填写进度 == 1000 视为wbs完成,后续不再计算wbs进度
|
if (curJd == 1000) {
|
result.setWcjd(1);
|
result.setJd(100);
|
projectClient.editLink(result);
|
return;
|
}
|
|
//根据周报填写进度修改wbs进度
|
//wbs进度
|
int totalJd = 0;
|
for (int i = 0; i < length; i++) {
|
String user = users[i];
|
if (userWekMap.containsKey(user)) {
|
List<WekRecord> oList = userWekMap.get(user);
|
if (oList.size() < 1) continue;
|
//当前wbs进度最大一个
|
WekRecord record = oList.stream().filter(item -> item.getJd() != null).max(Comparator.comparing(WekRecord::getJd)).get();
|
if (record == null || record.getJd() == null) continue;
|
Integer jd = record.getJd();
|
totalJd += jd;
|
}
|
|
}
|
if (totalJd > 0 && length > 0) {
|
totalJd /= length;
|
result.setJd(totalJd);
|
//所有人完成才设置wbs为完成
|
if (totalJd >= 100) result.setWcjd(1);
|
projectClient.editLink(result);
|
}
|
|
|
}
|
|
/**
|
* 部门过滤,只需要sysOrgCode中数据
|
*
|
* @param wekRecord sysOrgCode需要包含的部门
|
* @param list 周报数据
|
* @return 过滤部门周报数据
|
*/
|
private List<WekRecord> departFilter(WekRecord wekRecord, List<WekRecord> list) {
|
if (!StringUtils.isEmpty(wekRecord.getSysOrgCode())) {
|
String sysOrgCode = wekRecord.getSysOrgCode();
|
String[] split = sysOrgCode.split(",");
|
List<String> departs = Arrays.asList(split);
|
return list.stream().filter(i -> {
|
AtomicBoolean allow = new AtomicBoolean(false);
|
String orgCode = i.getSysOrgCode();
|
departs.forEach(org -> {
|
if (orgCode!=null && orgCode.startsWith(org)) {
|
allow.set(true);
|
}
|
});
|
return allow.get();
|
}).collect(Collectors.toList());
|
}
|
return list;
|
}
|
|
/**
|
* 统计周报工时
|
*
|
* @param configMap 一年所有星期
|
* @param weekMap 数据库周报记录 key-周号 value-周报记录
|
* @param item 生成的数据
|
* @param subType 数据类型 1-项目相关 2-其他事项
|
*/
|
private void statisWeeklyGs(Map<Integer, String> configMap, Map<Integer, List<WekRecord>> weekMap, Map<String, Object> item, int subType) {
|
int SUB_TYPE_1 = 1;//项目相关工作
|
int SUB_TYPE_2 = 2;//日常事务工作
|
//TODO 此处遍历的是一年所有的星期
|
for (Map.Entry<Integer, String> week : configMap.entrySet()) {
|
|
if (weekMap.containsKey(week.getKey())) {
|
//统计项目内一周的工时 TODO week的key为周号;value为生成title的数据列
|
item.put(week.getValue(), weekMap.get(week.getKey()).stream().filter(wek -> wek.getGs() != null).mapToDouble(WekRecord::getGs).sum());
|
if (subType == SUB_TYPE_1) {
|
if (!item.containsKey("xmName")) item.put("xmName", weekMap.get(week.getKey()).get(0).getXmName());
|
} else if (subType == SUB_TYPE_2) {
|
if (!item.containsKey("xmName")) item.put("xmName", weekMap.get(week.getKey()).get(0).getExtName());
|
}
|
//数据列(dataIndex)的规则是 m+(月份)+w+(星期号),此处截取月份判断数据属于哪个季
|
int i = Integer.parseInt(week.getValue().substring(1, 2));
|
//统计四季数据 四季的数据列为(s1,s2,s3,s4)
|
if (i < 4) {
|
if (!item.containsKey("s1")) {
|
item.put("s1", item.get(week.getValue()));
|
} else {
|
Double sTotal = (Double) item.get("s1") + (Double) item.get(week.getValue());
|
item.put("s1", sTotal);
|
}
|
} else if (i > 3 && i < 7) {
|
if (!item.containsKey("s2")) {
|
item.put("s2", item.get(week.getValue()));
|
} else {
|
Double sTotal = (Double) item.get("s2") + (Double) item.get(week.getValue());
|
item.put("s2", sTotal);
|
}
|
} else if (i > 6 && i < 10) {
|
if (!item.containsKey("s3")) {
|
item.put("s3", item.get(week.getValue()));
|
} else {
|
Double sTotal = (Double) item.get("s3") + (Double) item.get(week.getValue());
|
item.put("s3", sTotal);
|
}
|
|
} else if (i > 9 && i < 13) {
|
if (!item.containsKey("s4")) {
|
item.put("s4", item.get(week.getValue()));
|
} else {
|
Double sTotal = (Double) item.get("s4") + (Double) item.get(week.getValue());
|
item.put("s4", sTotal);
|
}
|
}
|
|
|
} else {
|
item.put(week.getValue(), 0.0);
|
}
|
|
|
}
|
|
|
//四季总数据
|
item.put("total", 0.0);
|
for (int j = 1; j <= 4; j++) {
|
String season = "s" + j;
|
if (item.containsKey(season)) {
|
Double s = (Double) item.get(season);
|
Double t = (Double) item.get("total");
|
item.put("total", s + t);
|
} else {
|
//没有数据的季 设置工时为0
|
item.put(season, 0.0);
|
}
|
|
}
|
|
}
|
|
/**
|
* 生成周报年统计报表的titile
|
*/
|
private Map<String, Object> createStatisticsYearTitle() {
|
Map<String, Object> root = new HashMap<>();
|
//title
|
List<Map<String, Object>> res = new ArrayList<>();
|
//周号对应colmun
|
Map<Integer, String> map = new HashMap<>();
|
//当前年
|
int curYear = DateUtils.getCurYear();
|
//统计一年有多少周
|
int yearWeekCount = 0;
|
//统计一季有多少周
|
int seasonCount = 0;
|
//先加一列全年合计
|
Map<String, Object> yearMap = new HashMap<>();
|
yearMap.put("title", curYear + "年");
|
List<Map<String, Object>> countYearList = new ArrayList<>();
|
yearMap.put("children", countYearList);
|
|
Map<String, Object> yearItem = new HashMap<>();
|
yearItem.put("title", "总计");
|
yearItem.put("column", "total");
|
countYearList.add(yearItem);
|
|
Map<String, Object> yearItem2 = new HashMap<>();
|
yearItem2.put("title", "占比");
|
yearItem2.put("column", "prop");
|
countYearList.add(yearItem2);
|
|
|
res.add(yearMap);
|
int curSeason = 0;
|
int curMonth = DateUtils.getCurMonth();
|
if (curMonth < 4) {
|
curSeason = 1;
|
} else if (curMonth > 3 && curMonth < 7) {
|
curSeason = 2;
|
} else if (curMonth > 6 && curMonth < 10) {
|
curSeason = 3;
|
} else {
|
curSeason = 4;
|
}
|
//一年12个月
|
for (int i = 1; i <= 12; i++) {
|
|
//月
|
Map<String, Object> monthMap = new HashMap<>();
|
monthMap.put("title", i + "月");
|
List<Map<String, Object>> weekList = new ArrayList<>();
|
monthMap.put("children", weekList);
|
res.add(monthMap);
|
//季
|
if (i % 3 == 0) {
|
seasonCount++;
|
Map<String, Object> seasonMap = new HashMap<>();
|
seasonMap.put("title", "第" + seasonCount + "季度");
|
seasonMap.put("column", "s" + seasonCount);
|
seasonMap.put("cno", seasonCount);
|
seasonMap.put("curSeason", curSeason);
|
res.add(seasonMap);
|
}
|
|
|
LocalDate date = LocalDate.of(curYear, i, 1);
|
//获取当月第一天是星期几
|
int week = date.getDayOfWeek().getValue();
|
//这个月最后一天
|
date = date.with(TemporalAdjusters.lastDayOfMonth());
|
//获取这天是这个月的第几天
|
int dayOfMonth = date.getDayOfMonth();
|
//统计一个月有多少周 (TODO :此处分周逻辑保持和周报获取周逻辑一致,定义周日在哪个月则设定本周属于哪个月)
|
int monthWeekCount = 0;
|
for (int j = 1; j <= dayOfMonth; j++) {
|
LocalDate everyDay = LocalDate.of(curYear, i, j);
|
int d = everyDay.getDayOfWeek().getValue();
|
//System.err.println("日期:" + everyDay + "-星期:" + d);
|
if (d % 7 == 0) {
|
monthWeekCount++;
|
yearWeekCount++;
|
String weekToDayStartStr = DateUtils.weekToDayStartStr(yearWeekCount);
|
String weekToDayEndStr = DateUtils.weekToDayEndStr(yearWeekCount);
|
//System.out.println(i + "月:" + monthWeekCount + "周-No:" + yearWeekCount + "------" + weekToDayStartStr + "==" + weekToDayEndStr);
|
//添加每个月的周
|
Map<String, Object> weekMap = new HashMap<>();
|
weekMap.put("title", i + "月第" + monthWeekCount + "周");
|
weekMap.put("column", "m" + i + "w" + monthWeekCount);
|
weekMap.put("wstart", weekToDayStartStr);
|
weekMap.put("wend", weekToDayEndStr);
|
weekMap.put("wno", yearWeekCount);
|
weekMap.put("curWeek", DateUtils.getCurWeek());
|
weekList.add(weekMap);
|
|
map.put(yearWeekCount, "m" + i + "w" + monthWeekCount);
|
|
}
|
}
|
|
}
|
root.put("colmuns", res);
|
root.put("config", map);
|
return root;
|
}
|
|
|
//创建本周和上周数据模板
|
private List<WekWeekBean> createTemplateData() {
|
//当前周
|
int curWeekNo = DateUtils.getCurWeek();
|
//当前年
|
int curYear = DateUtils.getCurYear();
|
String curWeekStart = DateUtils.weekToDayStartStr(curWeekNo);
|
String curWeekEnd = DateUtils.weekToDayEndStr(curWeekNo);
|
//上周
|
int lastWeekNo = curWeekNo - 1;
|
String lastWeekStart = DateUtils.weekToDayStartStr(lastWeekNo);
|
String lastWeekEnd = DateUtils.weekToDayEndStr(lastWeekNo);
|
if (curWeekNo == 1) {
|
lastWeekNo = 52;
|
lastWeekStart = DateUtils.weekToDayStartStr(curYear-1, lastWeekNo);
|
lastWeekEnd = DateUtils.weekToDayEndStr(curYear-1,lastWeekNo);
|
}
|
|
//下周
|
int nextWeekNo = curWeekNo + 1;
|
String nextWeekStart = DateUtils.weekToDayStartStr(nextWeekNo);
|
String nextWeekEnd = DateUtils.weekToDayEndStr(nextWeekNo);
|
|
|
//本周数据(本周数据显示本周内容和下周计划)
|
List<WekWeekBean> rootList = new ArrayList<>();
|
WekWeekBean thisWeek = new WekWeekBean();
|
thisWeek.setShow(true);
|
thisWeek.setWeek(curWeekNo);
|
thisWeek.setStartDateStr1(curWeekStart);
|
thisWeek.setEndDateStr1(curWeekEnd);
|
String tws = DateUtils.weekToDayEndStr(curYear, curWeekNo, "yyyy-MM-dd");
|
thisWeek.setWeekInMonth(DateUtils.getWeekInMonth(tws,2));
|
thisWeek.setStartDateStr2(nextWeekStart);
|
thisWeek.setEndDateStr2(nextWeekEnd);
|
thisWeek.setYear(curYear);
|
//上周数据
|
WekWeekBean lastWeek = new WekWeekBean();
|
lastWeek.setShow(false);
|
lastWeek.setWeek(lastWeekNo);
|
lastWeek.setStartDateStr1(lastWeekStart);
|
lastWeek.setEndDateStr1(lastWeekEnd);
|
String lws = DateUtils.weekToDayEndStr(curYear, lastWeekNo, "yyyy-MM-dd");
|
lastWeek.setWeekInMonth(DateUtils.getWeekInMonth(lws,2));
|
lastWeek.setStartDateStr2(curWeekStart);
|
lastWeek.setEndDateStr2(curWeekEnd);
|
lastWeek.setYear(curYear);
|
if (curWeekNo == 1) {
|
lastWeek.setYear(curYear-1);
|
}
|
|
|
//周里面的4种类型 0-本周总结、1-本周计划外工作、2-下周计划、3-下周需协调事务
|
List<WekTypeBean> typeList1 = new ArrayList<>();
|
for (int i = 0; i < 4; i++) {
|
WekTypeBean type = new WekTypeBean(i, thisWeek.getWeek());
|
List<WekRecord> list = new ArrayList<>();
|
type.setWekList(list);
|
configTypeName(curWeekNo, type);
|
typeList1.add(type);
|
}
|
//周里面的4种类型 0-本周总结、1-本周计划外工作、2-下周计划、3-下周需协调事务
|
List<WekTypeBean> typeList2 = new ArrayList<>();
|
for (int i = 0; i < 4; i++) {
|
WekTypeBean type = new WekTypeBean(i, lastWeek.getWeek());
|
List<WekRecord> list = new ArrayList<>();
|
type.setWekList(list);
|
configTypeName(curWeekNo, type);
|
typeList2.add(type);
|
}
|
|
thisWeek.setTypeList(typeList1);
|
thisWeek.setShowDetail(true);
|
lastWeek.setTypeList(typeList2);
|
lastWeek.setShowDetail(true);
|
rootList.add(thisWeek);
|
rootList.add(lastWeek);
|
return rootList;
|
}
|
|
//创建空白数据
|
private List<WekWeekBean> createEmptyData(Integer year, Integer week,String username) {
|
|
String curWeekStart = DateUtils.weekToDayStartStr(week);
|
String curWeekEnd = DateUtils.weekToDayEndStr(week);
|
|
//下周
|
int nextWeekNo = week + 1;
|
String nextWeekStart = DateUtils.weekToDayStartStr(nextWeekNo);
|
String nextWeekEnd = DateUtils.weekToDayEndStr(nextWeekNo);
|
|
//本周数据(本周数据显示本周内容和下周计划)
|
List<WekWeekBean> rootList = new ArrayList<>();
|
WekWeekBean thisWeek = new WekWeekBean();
|
thisWeek.setShow(true);
|
thisWeek.setWeek(week);
|
thisWeek.setStartDateStr1(curWeekStart);
|
thisWeek.setEndDateStr1(curWeekEnd);
|
String tws = DateUtils.weekToDayEndStr(year, week, "yyyy-MM-dd");
|
thisWeek.setWeekInMonth(DateUtils.getWeekInMonth(tws,2));
|
thisWeek.setStartDateStr2(nextWeekStart);
|
thisWeek.setEndDateStr2(nextWeekEnd);
|
thisWeek.setYear(year);
|
thisWeek.setUsername(username);
|
|
//周里面的4种类型 0-本周总结、1-本周计划外工作、2-下周计划、3-下周需协调事务
|
List<WekTypeBean> typeList1 = new ArrayList<>();
|
for (int i = 0; i < 4; i++) {
|
WekTypeBean type = new WekTypeBean(i, thisWeek.getWeek());
|
List<WekRecord> list = new ArrayList<>();
|
type.setWekList(list);
|
configTypeName(week, type);
|
typeList1.add(type);
|
}
|
|
|
thisWeek.setTypeList(typeList1);
|
thisWeek.setShowDetail(true);
|
rootList.add(thisWeek);
|
|
return rootList;
|
}
|
|
/**
|
* 生成周标签名
|
*
|
* @param curWeek
|
* @param typeBean
|
*/
|
private void configTypeName(int curWeek, WekTypeBean typeBean) {
|
String thisWeekTypeName[] = {"本周总结", "本周计划外工作", "下周计划", "下周需协调事务"};
|
String lastWeekTypeName[] = {"上周总结", "上周计划外工作", "本周计划", "本周计划外工作"};
|
String normalWeekTypeName[] = {"工作总结", "计划外工作", "工作计划", "需协调事务"};
|
int type = typeBean.getType();
|
if (curWeek == typeBean.getWeek()) {
|
typeBean.setName(thisWeekTypeName[type]);
|
}/*else if((curWeek-1) == typeBean.getWeek() ){
|
typeBean.setName(lastWeekTypeName[type]);
|
}*/ else {
|
typeBean.setName(normalWeekTypeName[type]);
|
}
|
|
}
|
}
|