package com.sunda.spmsweb.overseacontroller;


import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.sunda.spmscommon.ResponseResult;
import com.sunda.spmsorder.entity.MaterialSap;
import com.sunda.spmsorder.service.IFileOperationService;
import com.sunda.spmsorder.service.IMaterialSapService;
import com.sunda.spmsoversea.dto.SafetyInventorySearchDTO;
import com.sunda.spmsoversea.entity.SafetyInventory;
import com.sunda.spmsoversea.excel.SafetyInventoryDtlExcel;
import com.sunda.spmsoversea.excel.SafetyInventoryExcel;
import com.sunda.spmsoversea.service.ISafetyInventoryService;
import com.sunda.spmsweb.util.ExcelUtil;
import com.sunda.spmsweb.util.ExportExcel;
import com.sunda.spmsweb.util.JWTUtil;
import com.sunda.spmswms.entity.WhsStorage;

import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;

import java.io.File;
import java.io.FileInputStream;
import java.io.InputStream;
import java.text.SimpleDateFormat;
import java.util.*;

import org.apache.commons.collections.CollectionUtils;
import org.apache.commons.collections.MapUtils;
import org.apache.poi.hssf.usermodel.HSSFWorkbook;
import org.apache.poi.ss.usermodel.Cell;
import org.apache.poi.ss.usermodel.CellType;
import org.apache.poi.ss.usermodel.PictureData;
import org.apache.poi.ss.usermodel.Row;
import org.apache.poi.ss.usermodel.Sheet;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletResponse;

/**
 * <p>
 * 安全库存表 前端控制器
 * </p>
 *
 * @author Wayne
 * @since 2022-01-04
 */
@RestController
@RequestMapping("/safetyInventory")
@Api(tags = "安全库存", description = "安全库存")
public class SafetyInventoryController {

    @Autowired
    ISafetyInventoryService iSafetyInventoryService;
    
    @Autowired
    IFileOperationService iFileOperationService;
    
    @Autowired
    IMaterialSapService iMaterialSapService;

    @RequestMapping("/getSafetyInventoryPage")
    @ApiOperation(value = "查询安全库存分页数据", notes = "查询安全库存分页数据\n" +
            "工厂代码必输，物料编号可选\n" +
            "示例参数如下：\n" +
            "{\n" +
            "\t\"werks\": \"GF02\",\n" +
            "\t\"materialNo\": \"210052745\",\n" +
            "\t\"current\": 1,\n" +
            "\t\"size\": 20\n" +
            "}", httpMethod = "POST")
    @RequiresPermissions("safetyInventory-getSafetyInventoryPage")
    public ResponseResult getSafetyInventoryPage(@RequestBody SafetyInventorySearchDTO safetyInventorySearchDTO){
        try {
            IPage iPage = iSafetyInventoryService.getSafetyInventoryPage(safetyInventorySearchDTO);
            return ResponseResult.success().add("safetyInventoryList", iPage);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/createSafetyInventory")
    @ApiOperation(value = "新建或更新安全库存", notes = "新建或更新安全库存\n" +
            "根据 werks，materialNo 判断有效数据是否存在，存在则更新，不存在则新增；\n" +
            "示例参数如下：\n" +
            "{\n" +
            "\t\"comments\": \"c\",\n" +
            "\t\"dataVersion\": 7667,\n" +
            "\t\"materialNo\": \"210052745\",\n" +
            "\t\"safetyInventoryYear\": 0.5,\n" +
            "\t\"emergencyReserveBasicUnit\": 5,\n" +
            "\t\"basicUnit\": \"PCS\",\n" +
            "\t\"uuid\": \"d4b94a39f14b3428e0530101007fbcd2\",\n" +
            "\t\"werks\": \"GF02\",\n" +
            "\t\"whsLocationCode\": \"2006\",\n" +
            "\t\"safetyQtyBasicUnit\": 10,\n" +
            "\t\"standardConsumptionLastYear\": 0.5,\n" +
            "\t\"remarks\": \"r\"\n" +
            "}", httpMethod = "POST")
    @RequiresPermissions("safetyInventory-createSafetyInventory")
    public ResponseResult createSafetyInventory(@RequestBody SafetyInventory safetyInventory){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return iSafetyInventoryService.createSafetyInventory(safetyInventory, userId);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/deleteSafetyInventory")
    @ApiOperation(value = "删除安全库存数据", notes = "删除安全库存数据\n" +
            "示例数据：uuid = d4b94a39f14b3428e0530101007fbcd2, dataVersion = 7668", httpMethod = "POST")
    @RequiresPermissions("safetyInventory-deleteSafetyInventory")
    public ResponseResult deleteSafetyInventory(@RequestParam String uuid, @RequestParam Integer dataVersion){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return iSafetyInventoryService.deleteSafetyInventory(uuid, dataVersion, userId);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/getStandardConsumption")
    @ApiOperation(value = "获取工厂物料上年度标准消耗用量", notes = "获取工厂物料上年度标准消耗用量\n" +
            "耗用量目前仅参考 OVERSEA_WHS_OUT_DTL、OVERSEA_WHS_OUT 出库任务表；\n" +
            "示例数据：werks = GF02, materialNo = 210051422 或 210050469，当前年分数据 yearNumber = 2022", httpMethod = "POST")
    public ResponseResult getStandardConsumption(@RequestParam String werks,
                                                 @RequestParam String materialNo,
                                                 @RequestParam Integer yearNumber){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return iSafetyInventoryService.getStandardConsumption(werks, materialNo, yearNumber);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/getBelowSafetyInventory")
    @ApiOperation(value = "获取低于安全库存报表数据", notes = "获取低于安全库存报表数据\n" +
            "获取指定工厂下，有安全库存数量信息 且 对应物料库存数量 低于 安全库存数量的数据\n" +
            "示例数据：werks = TF02", httpMethod = "POST")
    @RequiresPermissions("safetyInventory-getBelowSafetyInventory")
    public ResponseResult getBelowSafetyInventory(@RequestParam String werks){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return iSafetyInventoryService.getBelowSafetyInventory(werks);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    /**
     * 导出低于安全库存报表
     */
    @RequestMapping("/exportBelowSafetyInventory")
    @ApiOperation(value = "导出低于安全库存报表数据", notes = "获取低于安全库存报表数据\n" +
            "获取指定工厂下，有安全库存数量信息 且 对应物料库存数量 低于 安全库存数量的数据\n" +
            "示例数据：werks = TF02", httpMethod = "POST")
    public void exportBelowSafetyInventory(@RequestParam String werks, HttpServletResponse response) {
        try {
            if (StringUtils.isEmpty(werks)){
                throw new Exception("工厂不允许为空");
            }
            ResponseResult result =  iSafetyInventoryService.getBelowSafetyInventory(werks);
            List<Map<String, Object>> belowSafetyInventoryList = (List<Map<String, Object>>) result.getData().get("belowSafetyInventoryList");
            List<SafetyInventoryExcel> itemList = new ArrayList<SafetyInventoryExcel>();
            if(belowSafetyInventoryList!=null && belowSafetyInventoryList.size()>0) {
                for (int i = 0; i < belowSafetyInventoryList.size(); i++) {
                    Map<String,Object> map = (Map<String,Object>) belowSafetyInventoryList.get(i);
                    SafetyInventoryExcel report = JSONObject.parseObject(JSONObject.toJSONString(map), SafetyInventoryExcel.class);
                    itemList.add(report);
                }
            }
            SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmss");
            String dateTime = sdf.format(new Date() );
            ExcelUtil.export(response, "BelowSafetyInventory" + dateTime, "bodyData", itemList, SafetyInventoryExcel.class);
        }catch (Exception e){
            e.printStackTrace();
        }
    }


    /**
     * 导出安全库存报表
     */
    @RequestMapping("/exportSafetyInventoryDtl")
    @ApiOperation(value = "导出安全库存报表数据", notes = "获取安全库存报表数据\n" +
            "示例数据：werks = TF02", httpMethod = "POST")
    public void exportSafetyInventoryDtl(@RequestParam String werks,String materialNo ,HttpServletResponse response) {
        try {
            ResponseResult result = iSafetyInventoryService.exportSafetyInventoryDtl(werks, materialNo);
            List<Map<String, Object>> safetyInventoryDtl = (List<Map<String, Object>>) result.getData().get("exportSafetyInventoryDtl");
            List<SafetyInventoryDtlExcel> itemList = new ArrayList<SafetyInventoryDtlExcel>();
            if(result!=null && safetyInventoryDtl.size()>0) {
                for (int i = 0; i < safetyInventoryDtl.size(); i++) {
                    Map<String,Object> map = (Map<String,Object>) safetyInventoryDtl.get(i);
                    SafetyInventoryDtlExcel report = JSONObject.parseObject(JSONObject.toJSONString(map), SafetyInventoryDtlExcel.class);
                    itemList.add(report);
                }
            }
            SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMddHHmmss");
            String dateTime = sdf.format(new Date() );
            ExcelUtil.export(response, "SafetyInventoryDtlExcel" + dateTime, "bodyData", itemList, SafetyInventoryDtlExcel.class);
        }catch (Exception e){
            e.printStackTrace();
        }
    }


    @SuppressWarnings({ "unused", "resource", "unchecked" })
	@RequestMapping("/importSafetyInventoryExcel")
    @ApiOperation(value = "Excel导入安全库存数据", notes = "请求参数示例：{ avatar: file}", httpMethod = "POST")
    @RequiresPermissions("safetyInventory-importSafetyInventoryExcel")
    @ResponseBody
    public ResponseResult importSafetyInventoryExcel(@RequestParam(value = "avatar") MultipartFile avatar){
    	if (avatar.isEmpty()) {
            return ResponseResult.error("不能上传空文件");
        }else {
            Sheet sheet = null;
            Row row;
            File temp = null;
            InputStream is;
            try {
                // 另存文件名
                SimpleDateFormat df = new SimpleDateFormat("yyyyMMddHHmmss");
                Calendar calendar = Calendar.getInstance();
                String fileName = df.format(calendar.getTime()) + avatar.getOriginalFilename();
                // 1.附件缓存路径
                String filePath = iFileOperationService.saveMaterialApplicationPic(avatar, fileName);
                // 2.上传附件至minIO文件服务器
                //String fileUrl = iFileOperationService.fileUploader(fileName, filePath);
                //return ResponseResult.success().add("imageUrl",fileUrl);
                temp = new File(filePath);
                is = new FileInputStream(temp);
                Workbook wb;
                Map<String, PictureData> sheetIndexPicMap;
                if (temp.getName().toLowerCase().endsWith(".xls")) {
                    wb = new HSSFWorkbook(is);
                    sheet = wb.getSheetAt(0);// 读取第一个sheet
                } else if (temp.getName().toLowerCase().endsWith(".xlsx")) {
                    wb = new XSSFWorkbook(is);
                    sheet = wb.getSheetAt(0);// 读取第一个sheet
                } else {
                    return ResponseResult.error("只支持excel格式文件！");
                }
                // 得到总行数
                int rowNum = sheet.getLastRowNum();
                if (rowNum <= 1) {
                    return ResponseResult.error("请检查文件内容是否为空！");
                }
                try {
                    List<SafetyInventory> safetyList = new ArrayList<SafetyInventory>();
                    for (int i = 2; i <= rowNum; i++) {//正式数据从第三行开始
                        row = sheet.getRow(i);
                        // 手工转化
                        if (row == null){
                            continue;
                        }
                        SafetyInventory safetyInventory=new SafetyInventory();
                        String cell0 = ExportExcel.getCellFormatValue(row.getCell(0));
                        if(StringUtils.isNotEmpty(cell0)){
                        	safetyInventory.setWerks(cell0);//工厂代码
                        }else{
                            return ResponseResult.error("第"+(i+1)+"行“工厂代码”不能为空！");
                        }
                        String cell1 = ExportExcel.getCellFormatValue(row.getCell(1));
                        if(StringUtils.isNotEmpty(cell1)){
                        	safetyInventory.setWhsLocationCode(cell1);//仓库编号
                        }else{
                            return ResponseResult.error("第"+(i+1)+"行“仓库编号”不能为空！");
                        }
                        String cell2 = ExportExcel.getCellFormatValue(row.getCell(2));
                        if(StringUtils.isNotEmpty(cell2)){
                        	safetyInventory.setMaterialNo(cell2);//物料编码
                        }else{
                        	return ResponseResult.error("第"+(i+1)+"行“物料编码”不能为空！");
                        }
                        // 判断物料编码是否存在
                        List<Map<String, Object>> materialList = iMaterialSapService.searchMaterialSapByNo(cell2);
                        if (CollectionUtils.isEmpty(materialList)) {
                        	return ResponseResult.error("第"+(i+1)+"行“物料编码”不存在！");
                        }
                    	safetyInventory.setBasicUnit(materialList.get(0).get("basicUnit").toString());//基本单位
                        
//                        if(row.getCell(3) != null){
//                        }
                    	String cell5 = ExportExcel.getCellFormatValue(row.getCell(5));
                        if(StringUtils.isNotEmpty(cell5)){
                    		safetyInventory.setClassify(cell5);//分类
                    	}
                        String cell6 = ExportExcel.getCellFormatValue(row.getCell(6));
                    	if(StringUtils.isNotEmpty(cell6)){
                    		safetyInventory.setStandardConsumptionLastYear(Double.valueOf(cell6));//年耗用量
                        }else{
                        	safetyInventory.setStandardConsumptionLastYear(0.0);
                        }
                    	String cell7 = ExportExcel.getCellFormatValue(row.getCell(7));
                    	if(StringUtils.isNotEmpty(cell7)){
                    		safetyInventory.setSafetyInventoryYear(Double.valueOf(cell7));//安全库存年数
                    	} else {
                    		safetyInventory.setSafetyInventoryYear(0.5);
                    	}
                    	String cell8 = ExportExcel.getCellFormatValue(row.getCell(8));
                    	if(StringUtils.isNotEmpty(cell8)){
                    		safetyInventory.setEmergencyReserveBasicUnit(Double.valueOf(cell8));//应急库存
                    	} else {
                    		safetyInventory.setEmergencyReserveBasicUnit(0.0);
                    	}
                    	String cell9 = ExportExcel.getCellFormatValue(row.getCell(9));
                    	if(StringUtils.isNotEmpty(cell9)){
                    		safetyInventory.setSafetyQtyBasicUnit(Double.valueOf(cell9));//安全库存
                    	} else {
                    		safetyInventory.setSafetyQtyBasicUnit(0.0);
                    	}
                    	String cell10 = ExportExcel.getCellFormatValue(row.getCell(10));
                        if(StringUtils.isNotEmpty(cell10)){
                        	// 删除标识不为空就是删除
                        	safetyInventory.setSpmsStatus("0");
                        } else {
                        	safetyInventory.setSpmsStatus("1");
                        }
                        String cell11 = ExportExcel.getCellFormatValue(row.getCell(11));
                        if(StringUtils.isNotEmpty(cell11)){
                        	safetyInventory.setRemarks(cell11);//备注
                        }
                        safetyList.add(safetyInventory);
                    }
                    String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
                    ResponseResult res = iSafetyInventoryService.batchCreateSafety(safetyList, userId);
                    if(100 == res.getCode()){
                        return ResponseResult.error(res.getMsg());
                    }
                }catch (Exception e) {
                    return ResponseResult.error(e.getMessage());
                }
            }catch (Exception e) {
                return ResponseResult.error(e.getMessage());
            } finally {
                if (temp != null) {
                    boolean newFile = temp.delete();
                    if(!newFile){
                    }
                }
            }
            return ResponseResult.success().add("msg","S");
        }
    }

}
