package com.upyuns.platform.rs.website.controller;

import cn.hutool.core.collection.CollUtil;
import cn.hutool.core.convert.Convert;
import cn.hutool.core.io.FileUtil;
import cn.hutool.core.util.StrUtil;
import com.github.wxiaoqi.security.admin.constant.AdminCommonConstant;
import com.github.wxiaoqi.security.auth.client.annotation.IgnoreUserToken;
import com.github.wxiaoqi.security.common.msg.ObjectRestResponse;
import com.github.wxiaoqi.security.common.rest.BaseController;
import com.github.wxiaoqi.security.common.util.process.ResultCode;
import com.github.wxiaoqi.security.common.vo.PageDataVO;
import com.upyuns.platform.rs.gtdata.GtDataRestClient;
import com.upyuns.platform.rs.gtdata.GtFileInfo;
import com.upyuns.platform.rs.website.biz.DataMenuBiz;
import com.upyuns.platform.rs.website.biz.DataTempcacheBiz;
import com.upyuns.platform.rs.website.biz.FileDataBiz;
import com.upyuns.platform.rs.website.biz.GainDataBiz;
import com.upyuns.platform.rs.website.controller.web.GainDataController;
import com.upyuns.platform.rs.website.dto.FileDataDTo;
import com.upyuns.platform.rs.website.dto.GainDataDTO;
import com.upyuns.platform.rs.website.entity.DataMenu;
import com.upyuns.platform.rs.website.entity.DataTempcache;
import com.upyuns.platform.rs.website.entity.FileData;
import com.upyuns.platform.rs.website.entity.GainData;
import com.upyuns.platform.rs.website.vo.DataMenuTree;
import io.swagger.annotations.ApiModelProperty;
import lombok.Data;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.web.bind.annotation.*;
import tk.mybatis.mapper.entity.Example;

import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.function.Function;
import java.util.stream.Collectors;

import static com.github.wxiaoqi.security.common.constant.CommonConstants.SYS_TRUE;
import static com.upyuns.platform.rs.website.controller.AdminGaindataController.GainDataAdminDTO.STATISTICSTYPE_SUPPLIER;
import static com.upyuns.platform.rs.website.controller.AdminGaindataController.GainDataAdminDTO.STATISTICSTYPE_TOPMENU;

@RestController
@RequestMapping("Gaindata")
@Slf4j
public class AdminGaindataController extends BaseController<GainDataBiz, GainData> {


    @Autowired
    DataTempcacheBiz dataTempcacheBiz;

    @Autowired
    DataMenuBiz dataMenuBiz;

    @Autowired
    FileDataBiz fileDataBiz;

    @Value("${universal.baseUploadPath}")
    private String baseUploadPath ;

    @Value("${universal.gaindataPath}")
    private String gaindataPath ;

    @Autowired
    GtDataRestClient gtDataRestClient;

    @Override
    public ObjectRestResponse<GainData> baseAdd(@RequestBody GainData gainData) {
        super.baseAdd(gainData);
        GainData updateGainData = new GainData();
        updateGainData.setId(gainData.getId());
        //创建目录
        if(!FileUtil.exist(baseUploadPath+gaindataPath+"/"+gainData.getId())) {
            FileUtil.mkdir(baseUploadPath+gaindataPath+"/"+gainData.getId());
        }
        updateGainData.setDataPath(baseUploadPath+gaindataPath+"/"+gainData.getId());
        baseBiz.updateSelectiveById(updateGainData);
        return ObjectRestResponse.succ();
    }

    @RequestMapping(value = "/getPageList",method = RequestMethod.GET)
    public ObjectRestResponse<List<GainData>> getPageList(GainDataDTO dto) {
        Example example = new Example(GainData.class);
        Example.Criteria criteria = example.createCriteria();
        criteria.andEqualTo("isDel", 0);
//        if (StringUtils.isNotBlank(dto.getName())){
//            criteria.andLike("title", "%" + dto.getName() + "%");
//        }
        example.setOrderByClause("crt_time desc");
        PageDataVO pageDataVO = PageDataVO.pageInfo(dto.getPage(), dto.getLimit(), ()->baseBiz.selectByExample(example));
        return ObjectRestResponse.succ(pageDataVO);
    }


    @RequestMapping(value = "/deleteById",method = RequestMethod.DELETE)
    public ObjectRestResponse deleteById(Integer id) {
        GainData monitorimage = new GainData();
        monitorimage.setId(id);
        monitorimage.setIsDel(1);
        baseBiz.updateSelectiveById(monitorimage);
        return ObjectRestResponse.succ();
    }




    @ApiModelProperty("查看文件列表")
    @RequestMapping(value = "/getFileDataList",method = RequestMethod.GET)
    public ObjectRestResponse<PageDataVO<FileData>> getList(FileDataDTo fileDataDTo){
        return ObjectRestResponse.succ(fileDataBiz.selectLogicAlls(fileDataDTo));
    }



    @ApiModelProperty("添加修改文件")
    @RequestMapping(value = "/addFileData",method = RequestMethod.POST)
    public ObjectRestResponse <FileData> addislandShip(@RequestBody FileData fileData) {

        if(null != fileData.getDatatempId()) {
            DataTempcache dataTempcache = dataTempcacheBiz.selectById(fileData.getId());
            fileData.setFilename(dataTempcache.getFilename());
            fileData.setFiletype(dataTempcache.getFiletype());
            fileData.setFilesize(dataTempcache.getFilesize());
            fileData.setGtdataPath(dataTempcache.getGtdataPath());
            fileData.setHasGtdata(dataTempcache.getHasGtdata());
            if(dataTempcache.getUptype() == DataTempcache.UPTYPE_UPLOAD || dataTempcache.getUptype() == DataTempcache.UPTYPE_URL ) {
                fileData.setFilepath(dataTempcache.getFilepath());
                fileData.setFileurl(dataTempcache.getFilename());
                fileData.setStoragetype(FileData.STORAGETYPE_UPLOAD);
            }else {
                fileData.setStoragetype(FileData.STORAGETYPE_GTDATA);
            }
        } if(null != fileData.getStoragetype() && FileData.STORAGETYPE_GTDATA == fileData.getStoragetype()) {
//            //gtdtat 获取数据
            Map<String, Object> responseMap = gtDataRestClient.list(fileData.getGtdataPath());
            if(null != responseMap && null != responseMap.get("HttpStatusCode") && null != responseMap.get("files") && 200 == (Integer) responseMap.get("HttpStatusCode")) {
//                (List<GtFileInfo>)responseMap.get("files")
                List<GtFileInfo> gtFileInfos = Convert.toList(GtFileInfo.class, responseMap.get("files"));
                GtFileInfo gtFileInfo = gtFileInfos.get(0);
                String filename = gtFileInfo.getFilename();
                String filesize = gtFileInfo.getSize();

                String filetype = filename.substring(filename.lastIndexOf("."));
                long fileSize = Long.valueOf(filesize);
                //  double fileSizeInKB = (double) fileSize / 1024; // 转换为 KB
                double fileSizeInMB = (double) fileSize / (1024 * 1024); // 转换为 MB
                double roundedFileSizeInMB = Math.round(fileSizeInMB * 100.0) / 100.0; // 保留两位小数
                String fileSizeString = String.format("%.2f MB", roundedFileSizeInMB);

                fileData.setHasGtdata(SYS_TRUE);
                fileData.setFilename(filename);
                fileData.setFiletype(filetype);
                fileData.setFilesize(fileSizeString);
            }else {
                return ObjectRestResponse.createFailedResult(ResultCode.FAILED_CODE, "分布式路径不对");
            }
        }

//        String name = fileData.getFilename();
//        List<FileData> islandShips = fileDataBiz.selectByWeekend(o -> {
//            o.andEqualTo(FileData::getFilename, name + "");
//            o.andEqualTo(FileData::getIsDel,0);
//            if (fileData.getId() != null) {
//                o.andNotEqualTo(FileData::getId, fileData.getId());  //修改的時候 不把自己搜出來
//            }
//            return  o;
//        });
//        if (islandShips.size()!=0){
//            return ObjectRestResponse.createFailedResult(ResultCode.EXIST_CODE, ResultCode.getMsg(ResultCode.EXIST_CODE));
//        }

        if (fileData.getId()!=null){
            fileDataBiz.updateSelectiveById(fileData);
        }else {
            fileData.setIsDel(0);
            fileDataBiz.insertSelective(fileData);
        }
        if(null != fileData.getGainId()) {
            baseBiz.updateSelectiveById(new GainData(){{
                setId(fileData.getGainId());
                setHasGtdata(HASGTDATA_UPD);
            }});
        }

        return ObjectRestResponse.succ();
    }

    @DeleteMapping("/filedeleteById")
    public ObjectRestResponse deleteInoPortAnalyse(Integer id) {
        FileData fileData = new FileData();
        fileData.setId(id);
        fileData.setIsDel(1);
        fileDataBiz.updateSelectiveById(fileData);
        return ObjectRestResponse.succ();
    }

    @ApiModelProperty("统计")
    @IgnoreUserToken
    @RequestMapping(value = "/app/unauth/statistics",method = RequestMethod.GET)
    public ObjectRestResponse<List<GainData>> statistics(GainDataAdminDTO dto) {
        Example example = baseBiz.initExample(dto);

        List<GainData> list = baseBiz.selectByExample(example);
        List<DataMenu> dataMenuList = dataMenuBiz.selectListAll();
        List<GainDataController.GainDataVO> voList = Convert.toList(GainDataController.GainDataVO.class, list);
        Map<Integer, DataMenu> dataMenuMap = dataMenuList.parallelStream().collect(Collectors.toMap(DataMenu::getId, Function.identity()));
        for(GainDataController.GainDataVO gainDataVO : voList) {
            if(null != gainDataVO.getMenuId()) {
                DataMenu topMenu = baseBiz.getTopMenu(dataMenuMap, dataMenuMap.get(gainDataVO.getMenuId()));
                if(null != topMenu) {
                    gainDataVO.setTopMenuId(topMenu.getId());
                    gainDataVO.setTopMenuName(topMenu.getTitle());
                }
            }
        }
        Map<String, Long> map = CollUtil.newHashMap();
        if(dto.getStatisticsType() == null || dto.getStatisticsType() == STATISTICSTYPE_SUPPLIER) {
                        map = list.parallelStream().filter(o -> StrUtil.isNotBlank(o.getSupplier())).collect(Collectors.groupingBy(GainData::getSupplier, Collectors.counting()));
        }else if(dto.getStatisticsType() == STATISTICSTYPE_TOPMENU) {
            map = voList.parallelStream().filter(o -> (null != o.getMenuId())).collect(Collectors.groupingBy(GainDataController.GainDataVO::getTopMenuName, Collectors.counting()));
        }

        return ObjectRestResponse.succ(map);
    }

    @ApiModelProperty("统计-供应商")
    @IgnoreUserToken
    @RequestMapping(value = "/app/unauth/statistics/supplier",method = RequestMethod.GET)
    public ObjectRestResponse statisticsSupplier(GainDataAdminDTO dto) {
        Example example = baseBiz.initExample(dto);

        List<GainData> list = baseBiz.selectByExample(example);
        List<DataMenu> dataMenuList = dataMenuBiz.selectListAll();
        List<GainDataController.GainDataVO> voList = Convert.toList(GainDataController.GainDataVO.class, list);
        Map<Integer, DataMenu> dataMenuMap = dataMenuList.parallelStream().collect(Collectors.toMap(DataMenu::getId, Function.identity()));
        for(GainDataController.GainDataVO gainDataVO : voList) {
            if(null != gainDataVO.getMenuId()) {
                DataMenu topMenu = baseBiz.getTopMenu(dataMenuMap, dataMenuMap.get(gainDataVO.getMenuId()));
                if(null != topMenu) {
                    gainDataVO.setTopMenuId(topMenu.getId());
                    gainDataVO.setTopMenuName(topMenu.getTitle());
                }
            }
        }

        List<SupplierStatistics> returnList = CollUtil.newArrayList();
        Map<String, Long> map = CollUtil.newHashMap();
        map = list.parallelStream().filter(o -> StrUtil.isNotBlank(o.getSupplier())).collect(Collectors.groupingBy(GainData::getSupplier, Collectors.counting()));
        handleTree(dto, returnList, map);
        return ObjectRestResponse.succ(returnList);
    }

    private void handleTree(GainDataAdminDTO dto, List<SupplierStatistics> returnList, Map<String, Long> map) {
        for(String supplierName : map.keySet()) {
            dto.setSupplier(supplierName);
            Example example = baseBiz.initExample(dto);

            List<GainData> list2 = baseBiz.selectByExample(example);
            List<DataMenu> dataMenuList = dataMenuBiz.selectListAll();
            List<GainDataBiz.DataMenuStats> dataMenuStatsList = Convert.toList(GainDataBiz.DataMenuStats.class, dataMenuList);
            List<GainDataController.GainDataVO> voList = Convert.toList(GainDataController.GainDataVO.class, list2);
            Map<Integer, GainDataBiz.DataMenuStats> dataMenuMap = dataMenuStatsList.parallelStream().collect(Collectors.toMap(DataMenu::getId, Function.identity()));
            for(GainDataController.GainDataVO gainDataVO : voList) {
                if(null != gainDataVO.getMenuId()) {
                    baseBiz.handleDataNum(dataMenuMap, dataMenuMap.get(gainDataVO.getMenuId()));
                }
            }
            List<GainDataBiz.DataMenuStats> dataMenuStats =  CollUtil.newArrayList(dataMenuMap.values());

            SupplierStatistics supplierStatistics = new SupplierStatistics();
            supplierStatistics.setSupplierName(supplierName);
            supplierStatistics.setNum(map.get(supplierName));
            supplierStatistics.setDatas(dataMenuBiz.getImageMenuStatsTree(dataMenuStats, AdminCommonConstant.ROOT));
            returnList.add(supplierStatistics);
        }
    }

    @Data
    public static class SupplierStatistics {
        private String supplierName;
        private Long num;
        private List<DataMenuTree> datas;
    }

    @ApiModelProperty("统计-目录")
    @IgnoreUserToken
    @RequestMapping(value = "/app/unauth/statistics/menu",method = RequestMethod.GET)
    public ObjectRestResponse statisticsMenu(GainDataAdminDTO dto) {
        Example example = baseBiz.initExample(dto);

        List<GainData> list = baseBiz.selectByExample(example);
        List<DataMenu> dataMenuList = dataMenuBiz.selectListAll();
        List<GainDataBiz.DataMenuStats> dataMenuStatsList = Convert.toList(GainDataBiz.DataMenuStats.class, dataMenuList);
        List<GainDataController.GainDataVO> voList = Convert.toList(GainDataController.GainDataVO.class, list);
        Map<Integer, GainDataBiz.DataMenuStats> dataMenuMap = dataMenuStatsList.parallelStream().collect(Collectors.toMap(DataMenu::getId, Function.identity()));
        for(GainDataController.GainDataVO gainDataVO : voList) {
            if(null != gainDataVO.getMenuId()) {
                baseBiz.handleDataNum(dataMenuMap, dataMenuMap.get(gainDataVO.getMenuId()));
            }
        }
        List<GainDataBiz.DataMenuStats> dataMenuStats =  CollUtil.newArrayList(dataMenuMap.values());

        return ObjectRestResponse.succ(dataMenuBiz.getImageMenuStatsTree(dataMenuStats, AdminCommonConstant.ROOT));
    }

    @Data
    static class GainDataAdminDTO extends GainDataDTO {
        public static final int STATISTICSTYPE_SUPPLIER = 1;
        public static final int STATISTICSTYPE_TOPMENU = 2;
        private Integer statisticsType;
    }
}
