package com.hssx.pcbms.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.hssx.pcbms.constant.Constant;
import com.hssx.pcbms.entity.*;
import com.hssx.pcbms.entity.vo.*;
import com.hssx.pcbms.mapper.*;
import com.hssx.pcbms.service.GoodsNoService;
import com.hssx.pcbms.service.GoodsService;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.hssx.pcbms.service.MaintainRecordService;
import com.hssx.pcbms.service.OperateRecordService;
import com.hssx.pcbms.util.*;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.multipart.MultipartFile;
import javax.annotation.Resource;
import javax.servlet.http.HttpServletResponse;
import java.text.SimpleDateFormat;
import java.time.LocalDate;
import java.time.format.DateTimeFormatter;
import java.util.*;
import java.util.stream.Collectors;

/**
 * <p>
 * 服务实现类
 * </p>
 *
 * @author 吴涛涛
 * @since 2019-10-25
 */
@Service
@Slf4j
public class GoodsServiceImpl extends ServiceImpl<GoodsMapper, Goods> implements GoodsService {
    @Resource
    private GoodsMapper goodsMapper;
    @Resource
    private GoodsNoMapper goodsNoMapper;
    @Resource
    private GoodsNoService goodsNoService;
    @Value("${upload.path}")
    private String path;
    @Resource
    private OperateRecordMapper operateRecordMapper;
    @Resource
    private UserMapper userMapper;
    @Resource
    private OperateRecordService operateRecordService;
    @Resource
    private MaintainRecordService maintainRecordService;
    @Resource
    private MaintainRecordMapper maintainRecordMapper;
    @Resource
    private GoodsTagsMapper goodsTagsMapper;
    @Resource
    private NewsNoticeMapper newsNoticeMapper;
    @Resource
    private NewsNoticeUserMapper newsNoticeUserMapper;
    @Resource
    private RacksEquipmentMapper racksEquipmentMapper;

    @Override
    public HttpRespMsg add(GoodsVO goodsVO) {
        HttpRespMsg msg = new HttpRespMsg();
        Goods goods = new Goods();
        BeanUtils.copyProperties(goodsVO, goods);
        List<GoodsNo> list = new ArrayList<>();
        goods.setSuffixCode(goodsVO.getGoodStr());
        goods.setDivisionCode(goodsVO.getDeptStr());
        goods.setCreatorId(goodsVO.getUserId());
        goodsMapper.insert(goods);
        String mouldNo = goodsVO.getDeptStr() + "-" + goodsVO.getGoodStr();
        Integer count = goodsNoMapper.selectCount(new QueryWrapper<GoodsNo>().eq("division_code", goodsVO.getDeptStr()).eq("suffix_code", goodsVO.getGoodStr()).last("limit 1"));
        if (count > 0) {
            msg.setError("当前编号组合已存在，请更换编号组合后重试。");
            return msg;
        }
        if (0 != goodsVO.getNumber()) {
            for (int i = 1; i <= goodsVO.getNumber(); i++) {
                GoodsNo goodsNo = new GoodsNo();
                goodsNo.setGoodsId(goods.getId());
                goodsNo.setModelNo(mouldNo + String.format("%04d", i));
                goodsNo.setSuffixCode(goodsVO.getGoodStr());
                goodsNo.setDivisionCode(goodsVO.getDeptStr());
                list.add(goodsNo);
            }
            goodsNoService.saveBatch(list);
        } else {
            msg.setError("资产数量必须大于零");
        }
        return msg;
    }

    @Override
    public HttpRespMsg updateInfo(Goods goods, MultipartFile file) {
        HttpRespMsg msg = new HttpRespMsg();
        goodsMapper.updateById(goods);
        return msg;
    }

    @Override
    public HttpRespMsg getList(PageUtil page, String keyName, Integer tagId, Integer uid) {
        System.out.println(tagId);
        HttpRespMsg msg = new HttpRespMsg();
        PageHelper.startPage(page.getPageNum(), page.getPageSize());
        List<GoodsVO> list = new ArrayList<>();
//        if(tagId != null){
//            if(tagId==-1){
//                //机柜列表
////                list = goodsMapper.getRackListBycondition(keyName, tagId, uid);
////                PageInfo<GoodsVO> info = new PageInfo<>(list);
////                msg.data = info;
////                return msg;
//            }else if(tagId==-2){
                //设备列表
//                QueryWrapper<GoodsNo> qw = new QueryWrapper();
//                if(keyName!=null && !"".equals(keyName)){
//                    qw.eq("device_name",keyName);
//                }
//                List <GoodsNo> equipmentList = goodsNoMapper.selectList(qw.eq("type",1).select("id", "model_no", "state","indate", "goods_id"
//                        ,"user_id", "update_indate", "is_maintain", "type", " device_name", "device_model", "good_sn_no",
//                        "label_id", "rack_id", "model_id", "u_bit_num","current_state","alarm_level").orderByDesc("id"));
//                PageInfo<GoodsNo> info = new PageInfo<>(equipmentList);
//                msg.data = info;
//                return msg;
//            }else{
//                list = goodsMapper.getListBycondition(keyName, tagId, uid);
//                PageInfo<GoodsVO> info = new PageInfo<>(list);
//                msg.data = info;
//                return msg;
//            }
//        }else{
        Integer goodType = 0;
        if(tagId !=null){
            if(tagId==-1){
                goodType = 1;
            }else if(tagId==-2){
                goodType = 2;
            }
        }
        if(goodType==0){
            list = goodsMapper.getListBycondition(keyName, tagId, uid);
            PageInfo<GoodsVO> info = new PageInfo<>(list);
            msg.data = info;
        }else{
            list = goodsMapper.getRackListBycondition(keyName, tagId, uid,goodType);
            PageInfo<GoodsVO> info = new PageInfo<>(list);
            msg.data = info;
        }
//        }
        return msg;
    }

    @Override
    public HttpRespMsg del(Goods goods) {
        HttpRespMsg msg = new HttpRespMsg();
        goods.setIsDelete(1);
        goodsMapper.updateById(goods);
        return msg;
    }

    @Override
    public HttpRespMsg delNo(GoodsNo goodsNo) {
        HttpRespMsg msg = new HttpRespMsg();
        GoodsNo no = goodsNoMapper.selectById(goodsNo.getId());
        if (no != null && no.getState() == 0) {
            goodsNoMapper.deleteById(goodsNo.getId());
        } else {
            msg.setError("操作失败，该编号对应的资产不存在或者处于非空闲状态。");
        }
        return msg;
    }

    @Override
    public HttpRespMsg getDetail(Integer id) {
        HttpRespMsg msg = new HttpRespMsg();
        Goods goods = goodsMapper.selectById(id);
        Map<String,Object> map = new HashMap<>();
        if(goods.getGoodType()!=0){
            List<Integer> equipmentIds = racksEquipmentMapper.selectList(new QueryWrapper<RacksEquipment>().eq("rack_goods_id", id)).stream().map(RacksEquipment::getEquipmentGoodsId).collect(Collectors.toList());
            if(equipmentIds.size()>0){
                List<GoodsVO> list = goodsMapper.getEuipmentList(equipmentIds);
                GoodsVO vo = goodsMapper.getDetail(id);
                map.put("rack",vo);
                map.put("equipments",list);
            }
            msg.data = map;
            return msg;
        }else{
            GoodsVO vo = goodsMapper.getDetail(id);
            msg.data = vo;
            return msg;
        }
    }

    @Override
    public HttpRespMsg handle(GoodsNo goodsNo, Integer currentUserId) {
        HttpRespMsg msg = new HttpRespMsg();
        User user = userMapper.selectById(currentUserId);
        GoodsNo no = goodsNoMapper.selectById(goodsNo.getId());
        goodsNo.setGoodsId(no.getGoodsId());
        goodsNoMapper.updateById(goodsNo);
        //添加处置记录
        OperateRecord operateRecord = new OperateRecord();
        String oldState = "";
        String nowState = "";
        if (no.getState() == 0) {
            oldState = "未用";
        } else if (no.getState() == 1){
            oldState = "在用";
            User usering = userMapper.selectById(no.getUserId());
            oldState = oldState + ("(" + usering.getName() + "/" + usering.getPhone() + ")");
        }
        if (goodsNo.getState() == 0) {
            nowState = "未用";
        } else if (goodsNo.getState() == 1) {
            nowState = "在用";
            User usering = userMapper.selectById(goodsNo.getUserId());
            nowState = nowState + ("(" + usering.getName() + "/" + usering.getPhone() + ")");
        } else if (goodsNo.getState() == 3) {
            nowState = "报废";
        }
        String content = Constant.HANDLE_CONTENT.replace("oldState", oldState).replace("newState", nowState);
        operateRecord.setContent(content);
        operateRecord.setGoodId(no.getGoodsId());
        operateRecord.setGoodNoId(no.getId());
        operateRecord.setGoodState(goodsNo.getState());
        operateRecord.setUserId(currentUserId);
        operateRecord.setUserName(user.getName());
        operateRecord.setModelNo(no.getModelNo());
        operateRecordMapper.insert(operateRecord);
        return msg;
    }

    @Override
    public HttpRespMsg operateList(Goods goods, PageUtil page) {
        HttpRespMsg msg = new HttpRespMsg();
        PageHelper.startPage(page.getPageNum(), page.getPageSize());
        List<OperateRecordVO> list = operateRecordMapper.selectCondition(goods);
        PageInfo<OperateRecordVO> info = new PageInfo<>(list);
        msg.data = info;
        return msg;
    }

    @Override
    public HttpRespMsg goodsNoDetailById(GoodsNo goodsNo) {
        HttpRespMsg msg = new HttpRespMsg();
        GoodsNo oldGoodsNo = goodsNoMapper.selectById(goodsNo.getId());
        GoodsNoVO vo = new GoodsNoVO();
        BeanUtils.copyProperties(oldGoodsNo, vo);
        User user = userMapper.selectById(oldGoodsNo.getUserId());
        if (user != null) {
            vo.setUsername(user.getName());
        }
        msg.data = vo;
        return msg;
    }

    @Override
    public HttpRespMsg goodsNoAdd(GoodsNo goodsNo, Integer count) {
        HttpRespMsg msg = new HttpRespMsg();
        GoodsNo oldGoodsNo = goodsNoMapper.selectOne(new QueryWrapper<GoodsNo>().eq("goods_id", goodsNo.getGoodsId()).orderByDesc("id").last("limit 1"));
        Goods goods = goodsMapper.selectById(goodsNo.getGoodsId());
        Integer start = 0;
        String prefix = goods.getDivisionCode()+"-"+goods.getSuffixCode();
        if(goods != null){
            if (oldGoodsNo != null) {
                start = Integer.parseInt(oldGoodsNo.getModelNo().substring(oldGoodsNo.getModelNo().length() - 4));
                List<GoodsNo> goodsNoList = new ArrayList<>();
                for (int i = 1; i <= count; i++) {
                    GoodsNo no = new GoodsNo();
                    String format = String.format("%04d", start + i);
                    BeanUtils.copyProperties(oldGoodsNo, no);
                    no.setModelNo(prefix + format);
                    no.setId(null);
                    goodsNoList.add(no);
                }
                if (!CollectionUtils.isEmpty(goodsNoList)) {
                    goodsNoService.saveBatch(goodsNoList);
                }
            } else {
                List<GoodsNo> goodsNoList = new ArrayList<>();
                for (int i = 1; i <= count; i++) {
                    GoodsNo no = new GoodsNo();
                    String format = String.format("%04d", start + i);
                    no.setModelNo(prefix + format);
                    no.setGoodsId(goodsNo.getGoodsId());
                    no.setDivisionCode(goods.getDivisionCode());
                    no.setSuffixCode(goods.getSuffixCode());
                    goodsNoList.add(no);
                }
                if (!CollectionUtils.isEmpty(goodsNoList)) {
                    goodsNoService.saveBatch(goodsNoList);
                }

            }
        }
        return msg;
    }

    @Override
    public HttpRespMsg distribute(GoodsNo goodsNo) {
        HttpRespMsg msg = new HttpRespMsg();
        Integer count = goodsNoMapper.selectCount(new QueryWrapper<GoodsNo>().eq("division_code", goodsNo.getDivisionCode()).eq("suffix_code", goodsNo.getSuffixCode()).last("limit 1"));
        if (count > 0) {
            msg.setError("当前编号组合已存在，请更换编号组合后重试。");
            return msg;
        }
        Goods goods = new Goods();
        goods.setDivisionCode(goodsNo.getDivisionCode());
        goods.setSuffixCode(goodsNo.getSuffixCode());
        goods.setId(goodsNo.getGoodsId());
        goodsMapper.updateById(goods);
        List<GoodsNo> goodsNoList = goodsNoMapper.selectList(new QueryWrapper<GoodsNo>().eq("goods_id", goodsNo.getGoodsId()));
        String suffixModelNo = goodsNo.getDivisionCode() + "-" + goodsNo.getSuffixCode();
        for (GoodsNo no : goodsNoList) {
            no.setModelNo(suffixModelNo + no.getModelNo().substring(no.getModelNo().length() - 4));
            no.setSuffixCode(goodsNo.getSuffixCode());
            no.setDivisionCode(goodsNo.getDivisionCode());
        }
        if (!CollectionUtils.isEmpty(goodsNoList)) {
            goodsNoService.updateBatchById(goodsNoList);
        }
        return msg;
    }

    @Override
    public HttpRespMsg maintain(MaintainRecordVO operateRecordVO) {
        HttpRespMsg msg = new HttpRespMsg();
        List<MaintainRecord> operateRecords = new ArrayList<>();
        if (null != operateRecordVO.getIds()) {
            List<Integer> idList = ListUtil.convertIntegerIdsArrayToList(operateRecordVO.getIds());
            for (Integer id : idList) {
                MaintainRecord operateRecord = new MaintainRecord();
                BeanUtils.copyProperties(operateRecordVO, operateRecord);
                operateRecord.setGoodsNoId(id);
                operateRecords.add(operateRecord);
            }
            maintainRecordService.saveBatch(operateRecords);
            //将原来待维护的状态更新为正常
            GoodsNo goodsNo = new GoodsNo();
            goodsNo.setGoodsId(operateRecordVO.getGoodsId());
            goodsNo.setIsMaintain(0);
            goodsNoMapper.update(goodsNo, new QueryWrapper<GoodsNo>().in("id", idList));
        } else {
            msg.setError("资产对应的编号id不存在");
        }
        return msg;
    }

    @Override
    public HttpRespMsg isMaintainList(Goods goods) {
        HttpRespMsg msg = new HttpRespMsg();
        List<GoodsNo> goodsNoList = goodsNoMapper.selectList(new QueryWrapper<GoodsNo>().eq("goods_id", goods.getId()).eq("is_maintain", 1));//1-需要保养
        msg.data = goodsNoList;
        return msg;
    }

    @Override
    public HttpRespMsg isMaintainRecord(Goods goods, PageUtil page) {
        HttpRespMsg msg = new HttpRespMsg();
        PageHelper.startPage(page.getPageNum(), page.getPageSize());
        List<MaintainRecordVO> list = maintainRecordMapper.getRecordList(goods);
        PageInfo<MaintainRecordVO> info = new PageInfo<>(list);
        msg.data = info;
        return msg;
    }

    @Override
    public HttpRespMsg myList(PageUtil page, String keyName, Integer uid) {
        HttpRespMsg msg = new HttpRespMsg();
        Integer start = (page.getPageNum() - 1) * page.getPageSize();
        List<GoodsVO> list = goodsMapper.selectMyList(start, page.getPageSize(), uid);
        Integer total = goodsMapper.selectMyList(null, null, uid).size();
        PageUtil<GoodsVO> pageInfo = new PageUtil<>();
        pageInfo.setList(list);
        pageInfo.setTotal(total);
        pageInfo.setPageSize(page.getPageSize());
        pageInfo.setPages(total);
        msg.data = pageInfo;
        return msg;
    }

    @Override
    public HttpRespMsg handelRecordExcel(Goods goods, HttpServletResponse response) {
        HttpRespMsg msg = new HttpRespMsg();
        List<OperateRecordVO> recordList = operateRecordMapper.selectCondition(goods);
        List<List<String>> list = new ArrayList<List<String>>();
        //标题
        List<String> titleList = new ArrayList<String>();
        titleList.add("资产编号");
        titleList.add("处置人");
        titleList.add("处置时间");
        titleList.add("操作内容");
        list.add(titleList);
        SimpleDateFormat dateSdf2 = new SimpleDateFormat("yyyy年MM月dd+HH时mm分ss秒");
        for (OperateRecordVO dynamic : recordList) {
            List<String> rowList = new ArrayList<String>();
            //资产编号
            rowList.add(dynamic.getModelNo());
            //处置人
            rowList.add(dynamic.getUserName());
            //处置时间
            rowList.add(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss").format(dynamic.getIndate()));
            //操作内容
            rowList.add(dynamic.getContent());
            list.add(rowList);
        }
        Goods newGoods = goodsMapper.selectById(goods.getId());
        String fileUrl = ExcelUtil.exportGeneralExcelByTitleAndList(response, newGoods.getName()+dateSdf2.format(new Date()), list, path);
        msg.data = fileUrl;
        return msg;
    }

    @Override
    public HttpRespMsg isMaintainExcel(Goods goods, HttpServletResponse response) {
        HttpRespMsg msg = new HttpRespMsg();
        List<MaintainRecordVO> recordList = maintainRecordMapper.getRecordList(goods);
        List<List<String>> list = new ArrayList<List<String>>();
        //标题
        List<String> titleList = new ArrayList<String>();
        titleList.add("资产编号");
        titleList.add("维护人");
        titleList.add("维护人号码");
        titleList.add("维护公司");
        titleList.add("维护公司电话");
        titleList.add("操作日期");
        list.add(titleList);
        SimpleDateFormat dateSdf2 = new SimpleDateFormat("yyyy年MM月dd+HH时mm分ss秒");
        for (MaintainRecordVO dynamic : recordList) {
            List<String> rowList = new ArrayList<String>();
            //资产编号
            rowList.add(dynamic.getModelNo());
            //维护人
            rowList.add(dynamic.getOperator());
            //维护人号码
            rowList.add(dynamic.getOperatorPhone());
            //维护公司
            rowList.add(dynamic.getCompany());
            //维护公司电话
            rowList.add(dynamic.getCompanyPhone());
            //操作日期
            rowList.add(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss").format(dynamic.getIndate())
            );
            list.add(rowList);
        }
        Goods newGoods = goodsMapper.selectById(goods.getId());
        String fileUrl = ExcelUtil.exportGeneralExcelByTitleAndList(response, newGoods.getName()+dateSdf2.format(new Date()), list, path);
        msg.data = fileUrl;
        return msg;
    }

    @Override
    public HttpRespMsg listExcel(PageUtil page, String keyName, Integer tagId, Integer uid,HttpServletResponse response) {
        HttpRespMsg msg = new HttpRespMsg();
        List<List<String>> list = new ArrayList<List<String>>();
        //标题
        List<String> titleList = new ArrayList<String>();
        titleList.add("资产名称");
        titleList.add("所属分类");
        titleList.add("型号");
        titleList.add("数量");
        titleList.add("单位");
        titleList.add("生产厂家");
        list.add(titleList);
        List<GoodsVO> goodsVOList = goodsMapper.getListBycondition(keyName, tagId, uid);
        List<GoodsTags> goodsTags = goodsTagsMapper.selectList(new QueryWrapper<>());
        SimpleDateFormat dateSdf2 = new SimpleDateFormat("yyyy年MM月dd+HH时mm分ss秒");
        for (GoodsVO dynamic : goodsVOList) {
            List<String> rowList = new ArrayList<String>();
            //资产名称
            rowList.add(dynamic.getName());
            //所属分类
            for (GoodsTags goodsTag : goodsTags) {
                if(dynamic.getTagId().equals(goodsTag.getId())){
                    rowList.add(goodsTag.getName());
                }
            }
            //型号
            rowList.add(dynamic.getModelNumber());
            //数量
            rowList.add(dynamic.getGoodsNos().size()+"");
            //单位
            rowList.add(dynamic.getUnit());
            //生产厂家
            rowList.add(dynamic.getFactory());
            list.add(rowList);
        }
        String fileUrl = ExcelUtil.exportGeneralExcelByTitleAndList(response, "资产"+dateSdf2.format(new Date()), list, path);
        msg.data = fileUrl;
        return msg;
    }

    @Override
    public HttpRespMsg goodsMaintainChecking() {
        HttpRespMsg msg = new HttpRespMsg();
        log.info("处理维护资产的定时任务启动了");
//        List<Goods> goodsLists = goodsMapper.selectList(new QueryWrapper<>());
        List<GoodsVO> goodsLists = goodsMapper.getListBycondition(null, null, null);
        String nowDate = DateTimeFormatter.ofPattern("yyyy-MM-dd").format(LocalDate.now());
        for (GoodsVO good : goodsLists) {
            if(nowDate.equals(good.getNextIndate())){
                GoodsNo no = new GoodsNo();
                no.setGoodsId(good.getId());
                no.setIsMaintain(1);
                //此处利用update配合修改条件和条件构造器来实现批量修改数据
                goodsNoMapper.update(no, new QueryWrapper<GoodsNo>().eq("goods_id", good.getId()));
                //条件通知消息
                NewsNotice newsNotice = new NewsNotice();
                newsNotice.setNoticeType(0);
                newsNotice.setRefId(good.getId());
                newsNotice.setRafName(good.getName());
                String content = Constant.GOODS_MATAIN_CONTENT;
                content = content.replace("name",good.getName()).replace("num",good.getGoodsNos().size()+good.getUnit());
                newsNotice.setContent(content);
                newsNoticeMapper.insert(newsNotice);
                List<User> users = userMapper.selectOperateUsersListByCondition();
                //通知所有操作员
                for (User user : users) {
                    NewsNoticeUser noticeUser = new NewsNoticeUser();
                    noticeUser.setNewsId(newsNotice.getId());
                    noticeUser.setUserId(user.getId());
                    newsNoticeUserMapper.insert(noticeUser);
                }
            }
        }
        return msg;
    }

    public static void main(String[] args) {
//        String format = String.format("%04d", 0);
//        System.out.println(format);
//        System.out.println("QWE-ASDF0001".substring(0, "QWE-ASDF0001".length() - 4));
//        System.out.println("QWE-ASDF0001".substring("QWE-ASDF0001".length() - 4));
//        System.out.println(Integer.parseInt("0001"));
        List<Integer> list = new ArrayList<>();
        System.out.println(list.stream().map(a ->a).collect(Collectors.toList()));
    }
}
