/**
 * Copyright &copy; 2015-2020 <a href="http://www.jeeplus.org/">JeePlus</a> All rights reserved.
 */
package com.jeeplus.modules.sg.managementcenter.materialproject.web;

import com.google.common.collect.Lists;
import com.google.common.collect.Maps;
import com.jeeplus.common.json.AjaxJson;
import com.jeeplus.common.utils.DateUtils;
import com.jeeplus.common.utils.StringUtils;
import com.jeeplus.common.utils.excel.ExportExcel;
import com.jeeplus.common.utils.excel.ImportExcel;
import com.jeeplus.core.persistence.Page;
import com.jeeplus.core.web.BaseController;
import com.jeeplus.modules.act.service.ActProcessService;
import com.jeeplus.modules.act.service.ActTaskService;
import com.jeeplus.modules.sg.audit.information.entity.append;
import com.jeeplus.modules.sg.managementcenter.activiti.utils.MyActiviUtils;
import com.jeeplus.modules.sg.managementcenter.activiti.utils.MyImportUtils;
import com.jeeplus.modules.sg.managementcenter.materialinfo.entity.MaterialInfo;
import com.jeeplus.modules.sg.managementcenter.materialinfo.service.MaterialInfoService;
import com.jeeplus.modules.sg.managementcenter.materialproject.entity.MaterialProject;
import com.jeeplus.modules.sg.managementcenter.materialproject.service.MaterialProjectService;
import com.jeeplus.modules.sg.managementcenter.materialproject.util.ImportUtil;
import com.jeeplus.modules.sg.managementcenter.materialproject.util.MaterialProUtil;
import com.jeeplus.modules.sg.managementcenter.project.entity.Project;
import com.jeeplus.modules.sg.managementcenter.project.service.ProjectService;
import com.jeeplus.modules.sg.managementcenter.project.util.ProjectImportUtil;
import com.jeeplus.modules.sg.materialmodule.activiti.entity.NonPower;
import com.jeeplus.modules.sg.materialmodule.activiti.service.NonPowerService;
import com.jeeplus.modules.sg.picking.activiti.entity.ShowList;
import com.jeeplus.modules.sg.picking.activiti.service.ShowListService;
import com.jeeplus.modules.sys.entity.DictValue;
import com.jeeplus.modules.sys.utils.UserUtils;
import org.activiti.engine.repository.ProcessDefinition;
import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
import org.apache.shiro.authz.annotation.Logical;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.http.HttpRequest;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.ModelAttribute;
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.multipart.MultipartFile;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import javax.validation.ConstraintViolationException;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;


@Controller
@RequestMapping(value = "${adminPath}/managementcenter/materialproject")
public class MaterialProjectController extends BaseController {

    @Autowired
    private MaterialProjectService materialProjectService;
    @Autowired
    private MaterialInfoService materialInfoService;
    @Autowired
    private ProjectService projectService;
    @Autowired
    private ShowListService showListService;
    @Autowired
    private ActProcessService actProcessService;
    @Autowired
    private ActTaskService actTaskService;
    @Autowired
    private NonPowerService nonPowerService;

    @ModelAttribute
    public MaterialProject get(@RequestParam(required = false) String id) {
        MaterialProject entity = null;
        if (StringUtils.isNotBlank(id)) {
            entity = materialProjectService.get(id);
        }
        if (entity == null) {
            entity = new MaterialProject();
        }
        return entity;
    }

    /**
     * 项目列表页面
     */
    @RequiresPermissions("managementcenter:materialproject:list")
    @RequestMapping(value = {"list", ""})
    public String list(MaterialProject materialProject, Model model) {
        model.addAttribute("materialProject", materialProject);
        return "modules/sg/managementcenter/materialproject/materialProjectList";
    }

    /**
     * 列表数据
     */
    @ResponseBody
    @RequiresPermissions("managementcenter:materialproject:list")
    @RequestMapping(value = "data")
    public Map<String, Object> data(MaterialProject materialProject, HttpServletRequest request, HttpServletResponse response, Model model) {
        materialProject.setProjectStatus("");
        MaterialProject materialProject1 = new MaterialProject();
        materialProjectService.getSearch(materialProject, materialProject1);
        HttpSession session = request.getSession();
        session.setAttribute("materialPro", materialProject1);
        Page<MaterialProject> page = materialProjectService.findPage(new Page<MaterialProject>(request, response), materialProject);
        return getBootstrapData(page);
    }

    /**
     * 查看，增加，编辑表单页面
     */
    @RequiresPermissions(value = {"managementcenter:materialproject:view", "managementcenter:materialproject:add", "managementcenter:materialproject:edit"}, logical = Logical.OR)
    @RequestMapping(value = "form")
    public String form(MaterialProject materialProject, Model model) {
        Boolean aBoolean = ProjectImportUtil.CHECKACQ(materialProject.getReserveProjectName());
        if (aBoolean) {
            model.addAttribute("aBoolean", true);
        } else {
            model.addAttribute("aBoolean", false);
        }
        model.addAttribute("materialProject", materialProject);
        return "modules/sg/managementcenter/materialproject/materialProjectForm";
    }

    /**
     * 保存
     */
    @ResponseBody
    @RequiresPermissions(value = {"managementcenter:materialproject:add", "managementcenter:materialproject:edit"}, logical = Logical.OR)
    @RequestMapping(value = "save")
    public AjaxJson save(MaterialProject materialProject, Model model) throws Exception {
        AjaxJson j = new AjaxJson();
        /**
         * 后台hibernate-validation插件校验
         */
        String errMsg = beanValidator(materialProject);
        if (StringUtils.isNotBlank(errMsg)) {
            j.setSuccess(false);
            j.setMsg(errMsg);
            return j;
        }
        //新增或编辑表单保存
        materialProjectService.save(materialProject);//保存
        ShowList showList = new ShowList();
        String projectId = materialProject.getProjectId();
        String projectName = materialProject.getProjectName();
        if (!"".equals(projectId) && !"".equals(projectName)) {
            String reserveProjectName = materialProject.getReserveProjectName();
            Project byName = projectService.findByName(materialProject.getReserveProjectName());
            if ("2".equals(byName.getPolicyStatus())) {
                String acquisitionStatus = byName.getAcquisitionStatus();
                if ("0".equals(acquisitionStatus)) {
                    showList.setTheNumber("1");
                    showList.setProjectName(projectName);
                    showList.setReserveProjectName(reserveProjectName);
                    showList.setProjectId(projectId);
                    showList.setsVersion(MyActiviUtils.findDic().getValue());
                    showListService.updateAcqStatus(reserveProjectName);
                    //保存数据
                    showListService.save(showList);
                    // 启动物资领料流程
                    Map<String, Object> vars = Maps.newHashMap();
                    vars.put("manager", UserUtils.getByUserName(byName.getAssignment().getOwnerManager()).getLoginName());
                    String procDefId = projectService.findDefId("wzll");
                    ProcessDefinition p = actProcessService.getProcessDefinition(procDefId);
                    String title = showList.getCurrentUser().getName() + "在" + DateUtils.getDateTime() + "发起" + p.getName();
                    actTaskService.startProcess(p.getKey(), "md_acquisition_process", showList.getId(), title, vars);
                }
                //判断是否需要发起土建领料流程(是否有土建工程量)
                boolean isEngineering = nonPowerService.findIsEngineering(reserveProjectName);
                if (isEngineering) {
                    if ("0".equals(byName.getAdvanceStatus())) {
                        NonPower nonPower = new NonPower();
                        nonPower.setProjectId(projectId);
                        nonPower.setProjectName(projectName);
                        nonPower.setReserveProjectName(reserveProjectName);
                        //保存土建基本数据
                        nonPowerService.insert(nonPower);
                        //修改项目基础信息土建流程状态
                        projectService.updateAdvanceStart(reserveProjectName, "1");
                        //启动土建流程
                        Map<String, Object> vars2 = Maps.newHashMap();
                        vars2.put("noPass", false);
                        vars2.put("pass", true);
                        vars2.put("manager", UserUtils.getByUserName(byName.getAssignment().getConstructionManage()).getLoginName());
                        String procDefId2 = projectService.findDefId("tjys");
                        ProcessDefinition p2 = actProcessService.getProcessDefinition(procDefId2);
                        String title2 = nonPower.getCurrentUser().getName() + "在" + DateUtils.getDateTime() + "发起" + p2.getName();
                        actTaskService.startProcess(p2.getKey(), "xm_nonpower_process", nonPower.getId(), title2, vars2);
                    }
                }else {
                    if ("0".equals(byName.getAdvanceStatus())) {
                        NonPower nonPower = new NonPower();
                        //修改项目基础信息土建流程状态
                        projectService.updateAdvanceStart(reserveProjectName, "1");
                        //启动土建流程
                        Map<String, Object> vars2 = Maps.newHashMap();
                        vars2.put("noPass", true);
                        vars2.put("pass", false);
                        vars2.put("design", UserUtils.getByUserName(byName.getAssignment().getConstructionManage()).getLoginName());
                        String procDefId2 = projectService.findDefId("tjys");
                        ProcessDefinition p2 = actProcessService.getProcessDefinition(procDefId2);
                        String title2 = nonPower.getCurrentUser().getName() + "在" + DateUtils.getDateTime() + "发起" + p2.getName();
                        actTaskService.startProcess(p2.getKey(), "xm_nonpower_process", nonPower.getId(), title2, vars2);
                    }
                }
            }
        }
        j.setSuccess(true);
        j.setMsg("保存项目成功");
        return j;
    }

    /**
     * 删除项目
     */
    @ResponseBody
    @RequiresPermissions("managementcenter:materialproject:del")
    @RequestMapping(value = "delete")
    public AjaxJson delete(MaterialProject materialProject) {
        AjaxJson j = new AjaxJson();
        materialProjectService.delete(materialProject);
        j.setMsg("删除项目成功");
        return j;
    }

    /**
     * 批量删除
     */
    @ResponseBody
    @RequiresPermissions("managementcenter:materialproject:del")
    @RequestMapping(value = "deleteAll")
    public AjaxJson deleteAll(String ids) {
        AjaxJson j = new AjaxJson();
        String[] idArray = ids.split(",");
        for (String id : idArray) {
            materialProjectService.delete(materialProjectService.get(id));
        }
        j.setMsg("删除项目成功");
        return j;
    }


    /**
     * 批量重置
     */
    @ResponseBody
    @RequiresPermissions("managementcenter:materialproject:reset")
    @RequestMapping(value = "reset")
    public AjaxJson reset(String ids) {
        AjaxJson j = new AjaxJson();
        String[] idArray = ids.split(",");
        for (String id : idArray) {
            materialProjectService.resetProject(materialProjectService.get(id));
        }
        j.setMsg("重置项目成功");
        return j;
    }

    /**
     * 物料列表导出
     */
    @ResponseBody
    @RequiresPermissions("managementcenter:materialproject:export")
    @RequestMapping(value = "export")
    public AjaxJson exportFile(MaterialProject materialProject, HttpServletRequest request, HttpServletResponse response) {
        AjaxJson j = new AjaxJson();
        HttpSession session = request.getSession();
        MaterialProject materialProject1 = (MaterialProject) session.getAttribute("materialPro");
        try {
            String fileName = "物料" + DateUtils.getDate("yyyyMMddHHmmss") + ".xlsx";
            List<MaterialProject> list = new ArrayList<MaterialProject>();
            if (!materialProject1.getReserveProjectName().equals("") || !materialProject1.getProjectName().equals("")
                    || !materialProject1.getReserveCode().equals("") || null != materialProject1.getReserveCodes() || null != materialProject1.getProjectCodes()) {
                list = materialProjectService.findList(materialProject1);
            } else {
                list = materialProjectService.findList(materialProject);
            }
            List<MaterialInfo> materialInfos = materialInfoService.findByBatch(list);
            new ExportExcel(null, MaterialInfo.class).setDataList(materialInfos).write(response, fileName).dispose();
            j.setSuccess(true);
            j.setMsg("导出成功！");
            return j;
        } catch (Exception e) {
            j.setSuccess(false);
            j.setMsg("导出失败！失败信息：" + e.getMessage());
        }
        return j;
    }


    /**
     * 年度物资上报模板下载
     */
    @ResponseBody
    @RequestMapping(value = "templates")
    public AjaxJson importFileTemplateS(HttpServletResponse response) {
        AjaxJson j = new AjaxJson();
        try {
            String fileName = "年度物资模板.xlsx";
            List<append> list = Lists.newArrayList();
            new ExportExcel("", MaterialProject.class, 1).setDataList(list).write(response, fileName).dispose();
            return null;
        } catch (Exception e) {
            j.setSuccess(false);
            j.setMsg("导入送审下载失败！失败信息：" + e.getMessage());
        }
        return j;
    }

    /**
     * 项目列表导出
     *
     * @param materialProject
     * @param request
     * @param response
     * @return
     */
    @ResponseBody
    @RequiresPermissions("managementcenter:materialproject:export")
    @RequestMapping(value = "exportpro")
    public AjaxJson exportPro(MaterialProject materialProject, HttpServletRequest request, HttpServletResponse response) {
        AjaxJson j = new AjaxJson();
        try {
            HttpSession session = request.getSession();
            MaterialProject materialProject1 = (MaterialProject) session.getAttribute("materialPro");
            String fileName = "项目表" + DateUtils.getDate("yyyyMMddHHmmss") + ".xlsx";
//			Page<MaterialProject> page = materialProjectService.findPage(new Page<MaterialProject>(request, response, -1), materialProject);
            List<MaterialProject> list = null;
            if (!materialProject1.getReserveProjectName().equals("") || !materialProject1.getProjectName().equals("")
                    || !materialProject1.getReserveCode().equals("") || null != materialProject1.getReserveCodes() || null != materialProject1.getProjectCodes()) {
                list = materialProjectService.findList(materialProject1);
            } else {
                list = materialProjectService.findList(materialProject);
            }
            new ExportExcel(null, MaterialProject.class).setDataList(list).write(response, fileName).dispose();
            j.setSuccess(true);
            j.setMsg("导出成功！");
            return j;
        } catch (Exception e) {
            j.setSuccess(false);
            j.setMsg("导出失败！失败信息：" + e.getMessage());
        }
        return j;
    }

    /**
     * 导入年度物资上报Excel数据-根据条件自动发送流程
     */
    @ResponseBody
    @RequiresPermissions("managementcenter:materialproject:import")
    @RequestMapping(value = "import")
    public AjaxJson importFile(@RequestParam("file") MultipartFile file, HttpServletResponse response, HttpServletRequest request) {
        AjaxJson j = new AjaxJson();
        try {
            ImportUtil importUtil = new ImportUtil(file, 0, 0);
//			Boolean materialProjectFlag = MaterialProUtil.getMaterialProjectFlag(importUtil);
            //获取导入表格所有数据
            List<MaterialProject> materialProjects = MaterialProUtil.getProjectUtil(importUtil);
            //新建表格用来存储符合现有项目信息的list
            List<MaterialProject> updateList = new ArrayList<>();
            //获取所以已经存在储备项目暂定名称的项目
            List<String> allReserveName = materialProjectService.findAllReserveName();
            //判断没有项目-结束导入
            if (allReserveName.size() <= 0) {
                j.setSuccess(true);
                return j;
            }
            //循环得出所有可以导入的项目信息list
            for (MaterialProject m : materialProjects) {
                for (String s : allReserveName) {
                    if (s.trim().equals(m.getReserveProjectName().trim())) {
                        updateList.add(m);
                    }
                }
            }
            //判断项目是否已经发起物资领料流程，若发送流程不可修改项目定义号及项目名称
            for (MaterialProject materialProject : updateList
            ) {
                Project byName = projectService.findByName(materialProject.getReserveProjectName());
                String acquisitionStatus = byName.getAcquisitionStatus();
                String advanceStatus = byName.getAdvanceStatus();
                String constructionStatus = byName.getConstructionStatus();
                String settStatus = byName.getSettStatus();
                //判断是否在流程中
                if (!"0".equals(acquisitionStatus) || !"0".equals(constructionStatus) || !"0".equals(settStatus) || !"0".equals(advanceStatus)) {
                    materialProject.setProjectId(byName.getProjectId());
                    materialProject.setProjectName(byName.getProjectName());
                }
            }
            //获取项目定义号和项目名称部位空的数据，便于判断项目定义号是否循环
            List<MaterialProject> needList = new ArrayList<>();
            for (MaterialProject m : updateList
            ) {
                String projectId = m.getProjectId();
                String projectName = m.getProjectName();
                if (null != projectId && !"".equals(projectId) && null != projectName && !"".equals(projectName)) {
                    needList.add(m);
                }
            }
            //获取可以发送施工交底流程，土建流程x项目信息
            for (MaterialProject pro : needList
            ) {
                ShowList showList = new ShowList();
                String projectId = pro.getProjectId();
                String projectName = pro.getProjectName();
                String reserveProjectName = pro.getReserveProjectName();
                Project byName = projectService.findByName(pro.getReserveProjectName());
                if ("2".equals(byName.getPolicyStatus())) {
                    String acquisitionStatus = byName.getAcquisitionStatus();
                    if ("0".equals(acquisitionStatus)) {
                        showList.setsVersion(MyActiviUtils.findDic().getValue());
                        showList.setTheNumber("1");
                        showList.setProjectName(projectName);
                        showList.setReserveProjectName(reserveProjectName);
                        showList.setProjectId(projectId);
                        showListService.updateAcqStatus(reserveProjectName);
                        //保存数据
                        showListService.save(showList);
                        // 启动物资领料流程
                        Map<String, Object> vars = Maps.newHashMap();
                        vars.put("manager", UserUtils.getByUserName(byName.getAssignment().getOwnerManager()).getLoginName());
                        String procDefId = projectService.findDefId("wzll");
                        ProcessDefinition p = actProcessService.getProcessDefinition(procDefId);
                        String title = showList.getCurrentUser().getName() + "在" + DateUtils.getDateTime() + "发起" + p.getName();
                        actTaskService.startProcess(p.getKey(), "md_acquisition_process", showList.getId(), title, vars);
                    }
                    //判断是否需要发起土建领料流程(是否有土建工程量)
                    boolean isEngineering = nonPowerService.findIsEngineering(reserveProjectName);
                    if (isEngineering) {
                        if ("0".equals(byName.getAdvanceStatus())) {
                            NonPower nonPower = new NonPower();
                            nonPower.setProjectId(projectId);
                            nonPower.setProjectName(projectName);
                            nonPower.setReserveProjectName(reserveProjectName);
                            //保存土建基本数据
                            nonPowerService.insert(nonPower);
                            //修改项目基础信息土建流程状态
                            projectService.updateAdvanceStart(reserveProjectName, "1");
                            //启动土建流程
                            Map<String, Object> vars2 = Maps.newHashMap();
                            vars2.put("design", UserUtils.getByUserName(byName.getAssignment().getConstructionManage()).getLoginName());
                            String procDefId2 = projectService.findDefId("tjys");
                            ProcessDefinition p2 = actProcessService.getProcessDefinition(procDefId2);
                            String title2 = nonPower.getCurrentUser().getName() + "在" + DateUtils.getDateTime() + "发起" + p2.getName();
                            actTaskService.startProcess(p2.getKey(), "xm_nonpower_process", nonPower.getId(), title2, vars2);
                        }
                    }
                }
            }
            if (updateList.size() > 0) {
                materialProjectService.updateList(updateList);
            }

            j.setMsg("已成功导入 " + updateList.size() + " 条项目表单记录");
        } catch (Exception e) {
            j.setSuccess(false);
            j.setMsg("导入项目表单失败！失败信息：" + e.getMessage());
        }
        return j;
    }
}