package com.sunda.spmsweb.overseacontroller;


import com.alibaba.fastjson.JSONObject;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.sunda.spmscommon.ResponseResult;
import com.sunda.spmsorder.service.IFileOperationService;
import com.sunda.spmsoversea.dto.*;
import com.sunda.spmsoversea.service.IOverseaRequisitionDtlService;
import com.sunda.spmsoversea.service.IOverseaRequisitionService;
import com.sunda.spmsweb.util.JWTUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
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.RestController;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import javax.servlet.http.HttpServletResponse;
import java.io.File;
import java.io.FileInputStream;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.URLEncoder;
import java.util.List;

/**
 * <p>
 * 领用申请表 前端控制器
 * </p>
 *
 * @author Wayne
 * @since 2021-09-22
 */
@RestController
@RequestMapping("/overseaRequisition")
@Api(tags = "海外仓领用申请", description = "海外仓领用申请")
public class OverseaRequisitionController {

    @Autowired
    IOverseaRequisitionService iOverseaRequisitionService;

    @Autowired
    IOverseaRequisitionDtlService iOverseaRequisitionDtlService;

    @Autowired
    IFileOperationService iFileOperationService;

    @RequestMapping("/getOverseaRequisitionPage")
    @ApiOperation(value = "获取领用申请表头分页", notes = "获取领用申请表头分页\n" +
            "示例参数：\n" +
            "{\n" +
            "\t\"beginDate\": \"\",\n" +
            "\t\"current\": 1,\n" +
            "\t\"endDate\": \"\",\n" +
            "\t\"size\": 20,\n" +
            "\t\"spmsId\": \"\",\n" +
            "\t\"spmsStatus\": \"\",\n" +
            "\t\"uuidRequisition\": \"\",\n" +
            "\t\"createUser\": \"999947\",\n" +
            "\t\"werks\": \"\",\n" +
            "\t\"whsLocationCode\": \"\",\n" +
            "\t\"workshopCode\": \"\"\n" +
            "}", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-getOverseaRequisitionPage")
    public ResponseResult getOverseaWhsInPage(@RequestBody OverseaRequisitionQueryDTO overseaRequisitionQueryDTO){
        try {
            return ResponseResult.success().add("overseaRequisitionList", iOverseaRequisitionService.getOverseaRequisitionPage(overseaRequisitionQueryDTO));
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }


    @RequestMapping("/getOverseaRequisitionReport")
    @ApiOperation(value = "获取领用单分析领用出库报表", notes = "获取领用单分析领用出库报表\n" +
            "示例参数：\n" +
            "{\n" +
            "\t\"beginDate\": \"\",\n" +
            "\t\"current\": 1,\n" +
            "\t\"endDate\": \"\",\n" +
            "\t\"size\": 20,\n" +
            "\t\"spmsId\": \"\",\n" +
            "\t\"materialNo\": \"\",\n" +
            "\t\"uuidRequisition\": \"\",\n" +
            "\t\"werks\": \"\",\n" +
            "\t\"whsLocationCode\": \"\",\n" +
            "\t\"workshopCode\": \"\"\n" +
            "}", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-getOverseaRequisitionReport")
    public ResponseResult getOverseaRequisitionReport(@RequestBody OverseaRequisitionReportDTO overseaRequisitionReportDTO){
        try {
            return ResponseResult.success().add("overseaRequisitionList", iOverseaRequisitionService.getOverseaRequisitionReport(overseaRequisitionReportDTO));
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }



    @RequestMapping("/createOverseaRequisitionReport")
    @ApiOperation(value = "生成领用单分析领用出库报表", notes = "生成领用单分析领用出库报表\n" +
            "示例参数：\n" +
            "{\n" +
            "\t\"beginDate\": \"\",\n" +
            "\t\"current\": 1,\n" +
            "\t\"endDate\": \"\",\n" +
            "\t\"size\": 20,\n" +
            "\t\"spmsId\": \"\",\n" +
            "\t\"materialNo\": \"\",\n" +
            "\t\"uuidRequisition\": \"\",\n" +
            "\t\"werks\": \"\",\n" +
            "\t\"whsLocationCode\": \"\",\n" +
            "\t\"workshopCode\": \"\"\n" +
            "}", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-createOverseaRequisitionReport")
    public ResponseResult createOverseaRequisitionReport(@RequestBody OverseaRequisitionReportDTO overseaRequisitionReportDTO){
        try {
            overseaRequisitionReportDTO.setCurrent(1);
            overseaRequisitionReportDTO.setSize(Integer.MAX_VALUE);
            String filename = "oversea_requisition_" + System.currentTimeMillis()+".xlsx";
            // 1.附件缓存路径
            String excelPath = iFileOperationService.saveOverseaRequisitionExcel(iOverseaRequisitionService.getOverseaRequisitionReport(overseaRequisitionReportDTO).getRecords(), filename);
            if (excelPath.isEmpty()){
                return ResponseResult.error("附件创建失败");
            }
            System.out.println("附件缓存地址：" + excelPath);
            // 2.上传附件至minIO文件服务器
            String fileUrl = iFileOperationService.fileUploader(filename, excelPath);
            if (fileUrl.isEmpty()){
                return ResponseResult.error("附件上传失败:" + excelPath + "--" + fileUrl);
            }
            System.out.println("附件上传地址:" + fileUrl);
            // 3.返回附件地址，上传OA
            return ResponseResult.success()
                    .add("fileUrl",fileUrl);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }


//    @RequestMapping("/downOverseaRequisitionReport")
//    @ApiOperation(value = "下载领用单分析领用出库报表", notes = "下载领用单分析领用出库报表\n" +
//            "示例参数:excelPath:'';filename:''; ", httpMethod = "GET")
//    public void downOverseaRequisitionReport(@RequestParam String excelPath,@RequestParam String filename){
//        try {
//            HttpServletResponse response = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes()).getResponse();
//            File file = new File(excelPath);
//            InputStream inputStream = new FileInputStream(file);
//            //强制下载不打开
//            response.setContentType("application/force-download");
//            OutputStream out = response.getOutputStream();
//            //使用URLEncoder来防止文件名乱码或者读取错误
//            response.setHeader("Content-Disposition", "attachment; filename=" + URLEncoder.encode(filename, "UTF-8"));
//            int b = 0;
//            byte[] buffer = new byte[10000];
//            while (b != -1) {
//                b = inputStream.read(buffer);
//                if (b != -1) {
//                    out.write(buffer, 0, b);
//                }
//            }
//            inputStream.close();
//            out.close();
//            out.flush();
//        }catch (Exception e){
//            e.printStackTrace();
//        }
//    }

    @RequestMapping("/getRequisitionAndDtl")
    @ApiOperation(value = "获取一条领用申请及其明细", notes = "获取领用申请及其明细\n" +
            "示例参数：uuidRequisition = cc913e66a42175f9e0530101007f5622, acfaf2eaf0824b8a912dbd22b0075e07\n" +
            "", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-getRequisitionAndDtl")
    public ResponseResult getRequisitionAndDtl(@RequestParam String uuidRequisition){
        try {
            return iOverseaRequisitionService.getRequisitionAndDtl(uuidRequisition);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/createOverseaRequisition")
    @ApiOperation(value = "新建领用申请", notes = "新建领用申请\n" +
            "状态说明：单据状态(0已删除;1待提交;2待审批;3审批通过;4审批拒绝;5已生成出库任务;)。\n" +
            "目标状态为：1 或 2；\n" +
            "示例参数：\n" +
            "{\n" +
            "\t\"comments\": \"\",\n" +
            "\t\"costCenter\": \"\",\n" +
            "\t\"createDate\": \"2021-09-23\",\n" +
            "\t\"businessType\": \"\",\n" +
            "\t\"relateDocument\": \"\",\n" +
            "\t\"remarks\": \"remarks\",\n" +
            "\t\"spmsStatus\": \"1\",\n" +
            "\t\"werks\": \"GF02\",\n" +
            "\t\"whsLocationCode\": \"2006\",\n" +
            "\t\"workshopCode\": \"EL\",\n" +
            "\t\"oaNumber\": \"3166-2022051227\",\n" +
            "\t\"requisitionDtlDTOList\": [{\n" +
            "\t\t\"applyQtyBasicUnit\": 2,\n" +
            "\t\t\"applyQtyUnitSales\": 2,\n" +
            "\t\t\"basicUnit\": \"PCS\",\n" +
            "\t\t\"materialNo\": \"210008387\",\n" +
            "\t\t\"remarks\": \"remarks\",\n" +
            "\t\t\"unitSales\": \"PCS\",\n" +
            "\t\t\"movementType\": \"Z03\",\n" +
            "\t\t\"actualMovementType\": \"Z04\"\n" +
            "\t}]\n" +
            "}", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-createOverseaRequisition")
    public ResponseResult createOverseaRequisition(@RequestBody OverseaRequisitionDTO overseaRequisitionDTO){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return iOverseaRequisitionService.createOverseaRequisition(overseaRequisitionDTO, userId);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/deleteOverseaRequisitionDtl")
    @ApiOperation(value = "删除领用申请一行明细", notes = "删除领用申请一行明细\n" +
            "示例参数：uuidRequisition = acfaf2eaf0824b8a912dbd22b0075e07; item = 30;\n" +
            "", httpMethod = "POST")
    public ResponseResult deleteOverseaRequisitionDtl(@RequestParam String uuidRequisition, @RequestParam Integer item){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            iOverseaRequisitionDtlService.deleteOverseaRequisitionDtl(uuidRequisition, item, userId);
            return iOverseaRequisitionService.getRequisitionAndDtl(uuidRequisition);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/addOverseaRequisitionDtl")
    @ApiOperation(value = "新增领用申请一行明细", notes = "新增领用申请一行明细\n" +
            "示例参数：\n" +
            "{\n" +
            "\t\"applyQtyBasicUnit\": 10,\n" +
            "\t\"applyQtyUnitSales\": 10,\n" +
            "\t\"basicUnit\": \"PCS\",\n" +
            "\t\"materialNo\": \"210008385\",\n" +
            "\t\"remarks\": \"ww\",\n" +
            "\t\"unitSales\": \"PCS\",\n" +
            "\t\"movementType\": \"Z01\",\n" +
            "\t\"uuidRequisition\": \"acfaf2eaf0824b8a912dbd22b0075e07\"\n" +
            "}", httpMethod = "POST")
    public ResponseResult addOverseaRequisitionDtl(@RequestBody OverseaRequisitionDtlDTO overseaRequisitionDtlDTO){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            int resp = iOverseaRequisitionDtlService.addOverseaRequisitionDtl(overseaRequisitionDtlDTO, userId);
            if (resp > 0){
                return iOverseaRequisitionService.getRequisitionAndDtl(overseaRequisitionDtlDTO.getUuidRequisition());
            }
            return ResponseResult.error("新增明细数据失败");
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/addOverseaRequisitionDtls")
    @ApiOperation(value = "新增领用申请多行明细", notes = "新增领用申请多行明细\n" +
            "示例参数：\n" +
            "[{\n" +
            "\t\"applyQtyBasicUnit\": 10,\n" +
            "\t\"applyQtyUnitSales\": 10,\n" +
            "\t\"basicUnit\": \"PCS\",\n" +
            "\t\"materialNo\": \"210008385\",\n" +
            "\t\"remarks\": \"ww\",\n" +
            "\t\"unitSales\": \"PCS\",\n" +
            "\t\"movementType\": \"Z01\",\n" +
            "\t\"uuidRequisition\": \"acfaf2eaf0824b8a912dbd22b0075e07\"\n" +
            "}]", httpMethod = "POST")
    public ResponseResult addOverseaRequisitionDtls(@RequestBody List<OverseaRequisitionDtlDTO> overseaRequisitionDtlDTOList){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            int resp = iOverseaRequisitionDtlService.addOverseaRequisitionDtls(overseaRequisitionDtlDTOList, userId);
            if (resp > 0){
                return iOverseaRequisitionService.getRequisitionAndDtl(overseaRequisitionDtlDTOList.get(0).getUuidRequisition());
            }
            return ResponseResult.error("新增明细数据失败");
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/updateOverseaRequisition")
    @ApiOperation(value = "领用申请更新", notes = "领用申请更新\n" +
            "状态说明：单据状态(0已删除;1待提交;2待审批;3审批通过;4审批拒绝;5已生成出库任务;)。\n" +
            "状态变化：1——1；1——2；4——2；4——4；2——3；\n" +
            "spmsStatus 为单据目标状态；\n" +
            "2——3 示例参数：\n" +
            "{\n" +
            "\t\"dataVersion\": 683,\n" +
            "\t\"spmsStatus\": \"2\",\n" +
            "\t\"approvalDate\": \"2022-01-10\",\n" +
            "\t\"remarks\": \"qq\",\n" +
            "\t\"comments\": \"qq\",\n" +
            "\t\"uuidRequisition\": \"acfaf2eaf0824b8a912dbd22b0075e07\",\n" +
            "\t\"requisitionDtlDTOList\": [{\n" +
            "\t\t\t\"actualQtyBasicUnit\": 2,\n" +
            "\t\t\t\"actualQtyUnitSales\": 2,\n" +
            "\t\t\t\"item\": 10,\n" +
            "\t\t\t\"uuidRequisition\": \"acfaf2eaf0824b8a912dbd22b0075e07\"\n" +
            "\t\t},\n" +
            "\t\t{\n" +
            "\t\t\t\"actualQtyBasicUnit\": 1,\n" +
            "\t\t\t\"actualQtyUnitSales\": 1,\n" +
            "\t\t\t\"item\": 20,\n" +
            "\t\t\t\"uuidRequisition\": \"acfaf2eaf0824b8a912dbd22b0075e07\"\n" +
            "\t\t}\n" +
            "\t]\n" +
            "}", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-updateOverseaRequisition")
    public ResponseResult updateOverseaRequisition(@RequestBody OverseaRequisitionDTO overseaRequisitionDTO){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return iOverseaRequisitionService.updateOverseaRequisition(overseaRequisitionDTO, userId);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }


    @RequestMapping("/approveOverseaRequisition")
    @ApiOperation(value = "领用申请审批通过", notes = "领用申请审批通过\n" +
            "状态说明：单据状态(0已删除;1待提交;2待审批;3审批通过;4审批拒绝;5已生成出库任务;)。\n" +
            "状态变化：1——1；1——2；4——2；4——4；2——3；\n" +
            "spmsStatus 为单据目标状态；\n" +
            "2——3 示例参数：\n" +
            "{\n" +
            "\t\"dataVersion\": 683,\n" +
            "\t\"spmsStatus\": \"2\",\n" +
            "\t\"approvalDate\": \"2022-01-10\",\n" +
            "\t\"remarks\": \"qq\",\n" +
            "\t\"comments\": \"qq\",\n" +
            "\t\"uuidRequisition\": \"acfaf2eaf0824b8a912dbd22b0075e07\",\n" +
            "\t\"requisitionDtlDTOList\": [{\n" +
            "\t\t\t\"actualQtyBasicUnit\": 2,\n" +
            "\t\t\t\"actualQtyUnitSales\": 2,\n" +
            "\t\t\t\"item\": 10,\n" +
            "\t\t\t\"uuidRequisition\": \"acfaf2eaf0824b8a912dbd22b0075e07\"\n" +
            "\t\t},\n" +
            "\t\t{\n" +
            "\t\t\t\"actualQtyBasicUnit\": 1,\n" +
            "\t\t\t\"actualQtyUnitSales\": 1,\n" +
            "\t\t\t\"item\": 20,\n" +
            "\t\t\t\"uuidRequisition\": \"acfaf2eaf0824b8a912dbd22b0075e07\"\n" +
            "\t\t}\n" +
            "\t]\n" +
            "}", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-approveOverseaRequisition")
    public ResponseResult approveOverseaRequisition(@RequestBody OverseaRequisitionDTO overseaRequisitionDTO){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return iOverseaRequisitionService.updateOverseaRequisition(overseaRequisitionDTO, userId);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/cancelOverseaRequisition")
    @ApiOperation(value = "领用申请退回/删除", notes = "领用申请退回/删除\n" +
            "状态说明：单据状态(0已删除;1待提交;2待审批;3审批通过;4审批拒绝;5已生成出库任务;)。\n" +
            "示例参数：uuidRequisition = cc913e66a42475f9e0530101007f5622；dataVersion = 686；spmsStatus = 4； \n" +
            "状态变化：2——4 审批拒绝；1——0，4——0 删除申请；", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-cancelOverseaRequisition")
    public ResponseResult cancelOverseaRequisition(@RequestParam String uuidRequisition, @RequestParam Integer dataVersion,  @RequestParam String spmsStatus){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return iOverseaRequisitionService.cancelOverseaRequisition(uuidRequisition, dataVersion, spmsStatus, userId);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }
    
    @RequestMapping("/rollBackOverseaRequisition")
    @ApiOperation(value = "领用申请撤回", notes = "领用申请撤回\n" +
            "状态说明：单据状态(0已删除;1待提交;2待审批;3审批通过;4审批拒绝;5已生成出库任务;)。\n" +
            "示例参数：uuidRequisition = cc913e66a42475f9e0530101007f5622；dataVersion = 686；\n", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-rollBackOverseaRequisition")
    public ResponseResult rollBackOverseaRequisition(@RequestParam String uuidRequisition, @RequestParam Integer dataVersion,@RequestParam String cancelReason){
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return iOverseaRequisitionService.rollBackOverseaRequisition(uuidRequisition, dataVersion, userId,cancelReason);
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }


    @RequestMapping("/getRequisitionOverdueReports")
    @ApiOperation(value = "待发货领用申请超期3天异常报表", notes = "待发货领用申请超期3天异常报表\n" +
            "状态说明：单据状态(0已删除;1待提交;2待审批;3审批通过;4审批拒绝;5已生成出库任务;)。\n" +
            "领用申请单状态为 3(审批通过) 审批通过日期已超过 3 天；且没有出库任务；\n" +
            "领用申请单状态为 5(已生成出库任务) 审批通过日期已超过 3 天；无有效出库任务 或 有状态为 1 进行中的出库任务；\n" +
            "示例参数：werks = TF02, currentDate = 2022-01-17；", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-getRequisitionOverdueReports")
    public ResponseResult getRequisitionOverdueReports(@RequestParam String werks, @RequestParam String currentDate){
//        if (StringUtils.isEmpty(werks) || StringUtils.isEmpty(currentDate)){
//            return ResponseResult.error("请求参数不能为空");
//        }
        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return ResponseResult.success().add("requisitionOverdueReports", iOverseaRequisitionService.getRequisitionOverdueReports(werks, currentDate));
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }

    @RequestMapping("/getReceiptAndDeliveryReports")
    @ApiOperation(value = "在途收货报表", notes = "在途收货报表\n" +
            "状态说明：单据状态(0已删除;1待提交;2待审批;3审批通过;4审批拒绝;5已生成出库任务;)。\n" +
            "领用申请单状态为 3(审批通过) 审批通过日期已超过 3 天；且没有出库任务；\n" +
            "领用申请单状态为 5(已生成出库任务) 审批通过日期已超过 3 天；无有效出库任务 或 有状态为 1 进行中的出库任务；\n" +
            "示例参数：werks = TF02, currentDate = 2022-01-17；", httpMethod = "POST")
    @RequiresPermissions("overseaRequisition-getReceiptAndDeliveryReports")
    public ResponseResult getReceiptAndDeliveryReports(@RequestBody OverseaReceiptAndDeliverySearchDTO overseaReceiptAndDeliverySearchDTO){

        try {
            String userId = JWTUtil.getUserId(SecurityUtils.getSubject().getPrincipal().toString());
            return ResponseResult.success().add("receiptAndDeliveryReports", iOverseaRequisitionService.getReceiptAndDeliveryReports(overseaReceiptAndDeliverySearchDTO));
        }catch (Exception e){
            e.printStackTrace();
            return ResponseResult.error("请求数据失败").add("error", e.getMessage());
        }
    }
}
