package com.jkcredit.invoice.controller.business;

import cn.afterturn.easypoi.excel.entity.ExportParams;
import cn.com.taiji.sdk.model.comm.protocol.eoms.company.B2bCompanyModel;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.jkcredit.invoice.annotation.LoginRequired;
import com.jkcredit.invoice.annotation.annotationdes.AuthenticationInterceptor;
import com.jkcredit.invoice.model.entity.CustomerRecharge;
import com.jkcredit.invoice.model.entity.customer.Customer;
import com.jkcredit.invoice.model.entity.customer.CustomerEtcChangeInfo;
import com.jkcredit.invoice.model.entity.customer.CustomerRec;
import com.jkcredit.invoice.model.entity.manager.Param;
import com.jkcredit.invoice.model.entity.user.User;
import com.jkcredit.invoice.service.customer.CustomerChangeInfoService;
import com.jkcredit.invoice.service.customer.CustomerRecService;
import com.jkcredit.invoice.service.customer.CustomerRechargeService;
import com.jkcredit.invoice.service.customer.CustomerService;
import com.jkcredit.invoice.service.lowerservice.CheckHasAuthRole;
import com.jkcredit.invoice.service.lowerservice.CustomeLowerService;
import com.jkcredit.invoice.service.manager.ParamService;
import com.jkcredit.invoice.util.DateUtil;
import com.jkcredit.invoice.util.ExportUtil;
import com.jkcredit.invoice.util.RespR;
import com.jkcredit.invoice.util.WordUtil;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang.StringUtils;
import org.apache.ibatis.annotations.Insert;
import org.apache.poi.util.IOUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import javax.servlet.http.HttpServletResponse;
import javax.validation.constraints.NotBlank;
import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.net.URLEncoder;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Date;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import static com.jkcredit.invoice.common.CommonConst.NO_CAR;
import static com.jkcredit.invoice.common.CommonConst.NULL;
import static com.jkcredit.invoice.common.CommonConst.SELF_CAR;

/**
 * 客户操作
 */
@Api(tags = "客户操作")
@RestController
@RequestMapping(value = {"/customer"})
/**
 * @Description 客户操作
 * @Author mashengyi
 * @Date 2022/2/8 18:16
 * @Param
 * @Return
 * @Exception
 *
 */
@Slf4j
public class CustomerController {
    @Autowired
    CustomerService customerService;
    @Autowired
    CustomerRechargeService customerRechargeService;

    @Autowired
    CustomeLowerService lowerService;

    @Autowired
    CustomerRecService customerRecService;
    @Autowired
    CustomerChangeInfoService customerChangeInfoService;
    @Autowired
    private ParamService paramService;
    @Autowired
    private CheckHasAuthRole checkHasAuthRole;

    /**
     * 分页查询客户
     *
     * @param page 参数集
     * @return 用户集合
     */
    @PostMapping("/findCustomer")
    @ApiOperation(value = "分页查询客户", notes = "分页查询客户")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR getCustomersByPage(Page page, Customer customer) {

        return new RespR(customerService.findAllCustomers(page, customer));
    }
    /**
     * 修改客户状态
     * @return 用户集合
     */
    @PostMapping("/updateCustomer")
    @ApiOperation(value="更新用户", notes="更新用户")
    @LoginRequired
    public RespR updateCustomer(@RequestBody  Customer customer) {
        return new RespR(customerService.updateCustomer(customer));
    }
    /**
     * 分页查询客户
     *
     * @param page 参数集
     * @return 用户集合
     */
    @PostMapping("/findCustomerRecharge")
    @ApiOperation(value = "分页查询客户充值信息", notes = "分页查询客户充值信息")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR findCustomerRecharge(Page page, CustomerRecharge customerRecharge) {

        return new RespR(customerRechargeService.findAllCustomerRecharge(page, customerRecharge));
    }

    /**
     * 分页查询客户
     *
     * @param page 参数集
     * @return 用户集合
     */
    @PostMapping("/findCustomerRechargeMoney")
    @ApiOperation(value = "分页查询客户端客户充值信息", notes = "分页查询客户端客户充值信息")
    @LoginRequired
    public RespR findCustomerRechargeMoney(Page page, CustomerRecharge customerRecharge, User user) {
        checkHasAuthRole.checkCustomerRole(user, customerRecharge.getCustomerName());
        return new RespR(customerRechargeService.findAllCustomerRechargeMoney(page, customerRecharge));
    }

    /**
     * 导出客户信息
     *
     * @param
     * @return 用户集合
     */
    @GetMapping("/findCustomerRecListExport")
    @ApiOperation(value = "客户信息导出", notes = "客户信息导出")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public void findCustomerRechargeExport(@NotBlank(message = "客户名称不能为空")String customerName, @NotBlank(message = "公司名称不能为空")String companyName, @NotBlank(message = "主体名称不能为空")String companyBelongName, HttpServletResponse response) throws Exception {
        CustomerRec customerRec = new CustomerRec();
        customerRec.setCustomerName(customerName);
        customerRec.setCompanyBelongName(companyBelongName);
        customerRec.setCompanyName(companyName);
        List<CustomerRec> customerRecs = customerRecService.findAllCustomerRecForExport(customerRec);

        if (customerRecs != null && customerRecs.size() > 0) {
            customerRecs.stream().forEach(customerRec1 -> {

                if (NO_CAR.equals(customerRec1.getBussinessType())) {
                    customerRec1.setBussinessType("无车");
                } else if (SELF_CAR.equals(customerRec1.getBussinessType())) {
                    customerRec1.setBussinessType("自有车");
                }
            });
        }
        ExportParams exportParams = new ExportParams("客户信息", "客户信息");
        ExportUtil.exportExcel(customerRecs, CustomerRec.class, "客户信息导出", exportParams, response);
    }

    /**
     * 分页查询客户注册信息
     *
     * @param page 参数集
     * @return 用户集合
     */
    @PostMapping("/findCustomerRecList")
    @ApiOperation(value = "分页查询客户注册信息", notes = "分页查询客户注册信息")
    @LoginRequired
    public RespR findCustomerRecList(Page page, CustomerRec customerRec, User user) {
        checkHasAuthRole.checkCustomerRole(user, customerRec.getCustomerName());
        return new RespR(customerRecService.findAllCustomerRec(page, customerRec));
    }

    /**
     * 修改客户状态
     *
     * @return 用户集合
     */
    @PostMapping("/customeRecStop")
    @ApiOperation(value = "停用备案用户", notes = "停用备案用户")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR customeRecStop(@RequestBody CustomerRec customerRec) {
        if (!checkHasAuthRole.checkMessage(customerRec.getCustomerName(), customerRec.getCompanyName())) {
            return new RespR(false, "停用备案用户失败，请查看数据是否维护准确");
        }
        customerRec.setRecStatus(4);
        return customerService.updateCustomerRecStatus(customerRec);
    }

    /**
     * 修改客户状态
     *
     * @return 用户集合
     */
    @PostMapping("/customeRecStart")
    @ApiOperation(value = "启用备案用户", notes = "启用备案用户")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR customeRecStart(@RequestBody CustomerRec customerRec) {
        if (!checkHasAuthRole.checkMessage(customerRec.getCustomerName(), customerRec.getCompanyName())) {
            return new RespR(false, "启用备案用户失败，请查看数据是否维护准确");
        }
        customerRec.setRecStatus(1);
        return customerService.updateCustomerRecStatus(customerRec);
    }

    /**
     * 修改客户状态
     *
     * @return 用户集合customerRecAdd
     */
    @PostMapping("/customerRecAdd")
    @ApiOperation(value = "手工添加备案信息", notes = "手工添加备案信息")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR customerRecAdd(@RequestBody @Validated CustomerRec customerRec) {
        customerRec.setInterType(1);
        List<CustomerRec> customerRecList = new ArrayList<>();
        customerRecList.add(customerRec);

        return lowerService.customeRec(customerRecList);
    }

    /**
     * 修改客户状态
     *
     * @return 用户集合customerRecAdd
     */
    @PostMapping("/customeRecQueryUpper")
    @ApiOperation(value = "查询备案信息", notes = "手工添加备案信息")
    @LoginRequired
    public RespR customeRecQueryUpper(@RequestBody @Validated({Insert.class}) CustomerRec customerRec, User user) {
        checkHasAuthRole.checkCustomerRole(user, customerRec.getCustomerName());
        RespR<List<B2bCompanyModel>> respR = customerService.customerRecQuery(customerRec);

        if (respR.getCode() == 1) {
            return respR;
        } else {
            List<B2bCompanyModel> resArr = respR.getData();
            if (resArr == null || resArr.size() == 0) {
                return new RespR(false, "未注册，无法回填");
            } else {

                if (resArr.size() >= 1) {
                    resArr.forEach(b2bCompanyModel -> {
                        if (b2bCompanyModel.getCompanyType().equals(customerRec.getCompanyType())) {
                            customerRec.setCompanyType(b2bCompanyModel.getCompanyType());
                            customerRec.setOperatingRangeType(b2bCompanyModel.getOperatingRangeType());
                            customerRec.setCompanyLeader(b2bCompanyModel.getContact());
                            customerRec.setCompanyLeaderPhone(b2bCompanyModel.getEmergencyTel());
                            customerRec.setCompanyAdress(b2bCompanyModel.getBuyerAddr());
                            customerRec.setCompanyPhone(b2bCompanyModel.getBuyerTel());
                            customerRec.setCompanyOpenbank(b2bCompanyModel.getBuyerBank());
                            customerRec.setCompanyOpenbankAcc(b2bCompanyModel.getBuyerBankAccount());

                        }
                    });
                }

                return new RespR(customerRec);
            }
        }


    }

    /**
     * 充值
     *
     * @return 用户集合
     */
    @PostMapping("/customRecharge")
    @ApiOperation(value = "账号充值", notes = "账号充值")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR customRecharge(@RequestBody @Validated CustomerRecharge customerRecharge) {
        return new RespR(customerService.customRecharge(customerRecharge));
    }

    @PostMapping("/customeRec")
    @ApiOperation(value = "用户备案确认", notes = "用户备案确认")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR customeRec(@RequestBody @Validated CustomerRec customerRec) {
        return customerService.customeRec(customerRec);
    }

    @PostMapping("/contractAdd")
    @ApiOperation(value = "协议上传确认", notes = "协议上传确认")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR contractAdd(@RequestBody CustomerRec customerRec) {
        if (!checkHasAuthRole.checkMessage(customerRec.getCompanyNum(), customerRec.getServiceStartTime(),
                customerRec.getServiceEndTime())) {
            return new RespR(false, "协议上传确认失败，请查看数据是否维护准确");
        }
        return customerService.contractAdd(customerRec);
    }
    @PostMapping("/promiseAdd")
    @ApiOperation(value = "承诺协议上传确认", notes = "承诺协议上传确认")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR promiseAdd(@RequestBody CustomerRec customerRec) {
        if (!checkHasAuthRole.checkMessage(customerRec.getCompanyNum(),customerRec.getPromiseFileName(),customerRec.getPromiseBase64Str())){
            return new RespR(false, "协议上传确认失败，请查看数据是否维护准确");
        }
        return customerService.promiseAdd(customerRec);
    }

    @PostMapping("/contractStatusFail")
    @ApiOperation(value = "协议上传失败状态确认", notes = "协议上传失败状态确认")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR contractStatusFail(@RequestBody CustomerRec customerRec) {
        if (null == customerRec.getRecStatus()) {
            return new RespR(false, "协议上传失败状态确认失败，请查看数据是否维护准确");
        }
        return customerService.contractStatusFail(customerRec);
    }


    @PostMapping("/customerRecEditMail")
    @ApiOperation(value = "更新备案邮箱", notes = "更新备案邮箱")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR customerRecEditMail(@RequestBody CustomerRec customerRec) {
        if (null == customerRec.getInvoiceMail() || null == customerRec.getCompanyName()) {
            return new RespR(false, "更新备案邮箱失败，请查看数据是否维护准确");
        }
        return customerService.customerRecEditMail(customerRec);
    }


    @PostMapping("/contractStatusProcess")
    @ApiOperation(value = "协议上传成功，审批中状态确认", notes = "协议上传成功，审批中状态确认")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR contractStatusProcess(@RequestBody CustomerRec customerRec) {
        if (null == customerRec.getRecStatus()) {
            return new RespR(false, "协议上传成功，审批中状态确认失败，请查看数据是否维护准确");
        }
        return customerService.contractStatusProcess(customerRec);
    }

    @PostMapping("/contractStatusSuccess")
    @ApiOperation(value = "备案成功状态确认", notes = "备案成功状态确认")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR contractStatusSuccess(@RequestBody CustomerRec customerRec) {
        if (null == customerRec.getRecStatus()) {
            return new RespR(false, "备案成功状态确认失败，请查看数据是否维护准确");
        }
        return customerService.contractStatusSuccess(customerRec);
    }

    @GetMapping("/contractDownload")
    @ApiOperation(value = "协议下载", notes = "协议下载")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR contractDownload(@NotBlank(message = "企业绑定ID不能为空")String customerRecId, HttpServletResponse response) {

        CustomerRec customerRec = (CustomerRec) customerService.contractDownload(customerRecId).getData();
        String fileName = customerRec.getLowerFileName();
        InputStream inputStream = null;
        OutputStream outputStream = null;
        if (customerRec.getLowerBase64Str() != null) {
            try {
                //将base64编码的字符串解码成字节数组
                byte[] byteArray = new sun.misc.BASE64Decoder().decodeBuffer(customerRec.getLowerBase64Str());
                inputStream = new ByteArrayInputStream(byteArray);
                response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8"));
                outputStream = response.getOutputStream();
                IOUtils.copy(inputStream, outputStream);
                response.flushBuffer();
                return new RespR(true);
            } catch (IOException e) {
                log.error("协议下载CustomerController.contractDownload协议下载失败{}", e.getMessage());
            } finally {
                IOUtils.closeQuietly(inputStream);
                IOUtils.closeQuietly(outputStream);
            }
        }

        return new RespR(false);
    }

    @GetMapping("/generateWord")
    @ApiOperation(value = "文档下载", notes = "文档下载")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR generateWord(@NotBlank(message = "企业绑定ID不能为空")String customerRecId, HttpServletResponse response) {

        CustomerRec customerRec = (CustomerRec) customerService.generateWordDownload(customerRecId).getData();
        if (null == customerRec || null == customerRec.getServiceStartTime() || null == customerRec.getServiceEndTime()) {
            return new RespR(false, "企业维护信息缺失服务时间，请手动维护");
        }
        String fileName = "合作说明.doc";
        Map<String, String> dataMap = new HashMap<>(10);
        dataMap.put("a", customerRec.getCompanyBelongName());
        dataMap.put("b", customerRec.getCompanyName());
        dataMap.put("c", customerRec.getCompanyReferencenum());
        dataMap.put("d", customerRec.getCompanyAdress());
        dataMap.put("e", customerRec.getCompanyPhone());
        dataMap.put("f", customerRec.getCompanyOpenbank());
        dataMap.put("g", customerRec.getCompanyOpenbankAcc());
        dataMap.put("j", customerRec.getServiceStartTime().substring(0, 10));
        dataMap.put("k", customerRec.getServiceEndTime().substring(0, 10));
        Calendar now = Calendar.getInstance();
        dataMap.put("l", now.get(Calendar.YEAR) + "");
        dataMap.put("h", (now.get(Calendar.MONTH) + 1) + "");
        dataMap.put("i", now.get(Calendar.DAY_OF_MONTH) + "");
        OutputStream outputStream = null;
        try {
            response.setHeader("Content-Disposition", "attachment;filename=" + URLEncoder.encode(fileName, "UTF-8"));
            outputStream = response.getOutputStream();
            WordUtil.exportSimpleWord(dataMap, "/static/templates/excel/", outputStream);
            response.flushBuffer();
        } catch (Exception e) {
            log.error("文档下载CustomerController.generateWord文档下载失败{}", e.getMessage());
        } finally {
            IOUtils.closeQuietly(outputStream);
        }
        return new RespR(false);
    }

    /**
     * 分页查询客户备案预警信息
     *
     * @param page 参数集
     * @return 用户集合
     */
    @PostMapping("/findCustomerRecTimeList")
    @ApiOperation(value = "客户备案预警查询", notes = "客户备案预警查询")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR findCustomerRecTimeList(Page page, CustomerRec customerRec) {
        IPage ipage = null;
        if (isaBoolean(customerRec)) {
            if (StringUtils.isNotEmpty(customerRec.getServiceEndTime()) && !NULL.equals(customerRec.getServiceEndTime())) {
                String[] res = customerRec.getServiceEndTime().split(",");
                customerRec.setServiceEndTimeStart(res[0]);
                customerRec.setServiceEndTimeEnd(res[1].replace("00:00:00", "23:59:59"));
            }
            ipage = customerRecService.findAllCustomerRecWarning(page, customerRec);

        } else {
            Param param = paramService.getParamsByParamName("CUST_EARLY_WARNING");
            ipage = customerRecService.findAllCustomerRecWarning(page, customerRec);
            List<CustomerRec> lists = ipage.getRecords();
            if (lists.size() > 0) {
                //遍历删除
                Iterator<CustomerRec> iterator = lists.iterator();
                while (iterator.hasNext()) {
                    CustomerRec customerRec1 = iterator.next();
                    if (((DateUtil.daysBetween(customerRec1.getServiceEndTime(), new Date()) < 0))
                            || (Integer.valueOf(param.getParamValue()) <= (DateUtil.daysBetween(customerRec1.getServiceEndTime(), new Date())))) {
                        iterator.remove();//使用迭代器的删除方法删除
                    }
                }
            }
            ipage.setTotal(lists.size());
        }

        return new RespR(ipage);
    }

    private boolean isaBoolean(CustomerRec customerRec) {
        return (StringUtils.isNotEmpty(customerRec.getServiceEndTime())
                && !NULL.equals(customerRec.getServiceEndTime())) ||
                (StringUtils.isNotEmpty(customerRec.getCompanyName()) && !NULL.equals(customerRec.getCompanyName())) ||
                (StringUtils.isNotEmpty(customerRec.getCompanyBelongName()) && !NULL.equals(customerRec.getCompanyBelongName()));
    }

    /**
     * 分页查询余额告警用户
     *
     * @param page 参数集
     * @return 用户集合
     */
    @PostMapping("/findCustomerMoney")
    @ApiOperation(value = "分页查询余额告警用户", notes = "分页查询余额告警用户")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR getCustomerMoneysByPage(Page page, Customer customer) {
        Param param = paramService.getParamsByParamName("CUST_MONEY_WARNING");
        IPage ipage = null;
        if (customer.getMoneyUpper() == null || customer.getMoneyUpper() == -1) {
            customer.setMoneyUpper(Double.valueOf(param.getParamValue()));
            ipage = customerService.findAllNomoneyCustomers(page, customer);
        } else if (customer.getMoneyUpper() == null || customer.getMoneyUpper() == 0) {
            ipage = customerService.findAllNomoneyCustomersByZero(page, customer);
        } else {
            ipage = customerService.findAllNomoneyCustomers(page, customer);
        }

        return new RespR(ipage);
    }

    /**
     * @param customerRec
     * @return
     */
    @PostMapping("/customeRecQueryListByPage")
    @ApiOperation(value = "用户备案列表分页查询", notes = "用户备案列表分页查询")
    @LoginRequired
    public RespR customeRecQueryListByPage(Page page, CustomerRec customerRec, User user) {
        checkHasAuthRole.checkCustomerRole(user, customerRec.getCustomerName());
        IPage ipage = customerRecService.findAllCustomerRec(page, customerRec);
        return new RespR(ipage);
    }

    /**
     * @param customerEtcChangeInfo
     * @return
     */
    @PostMapping("/customerChangeList")
    @ApiOperation(value = "用户换卡信息列表查询", notes = "用户换卡信息列表查询")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR customeChangeInfoListByPage(Page page, CustomerEtcChangeInfo customerEtcChangeInfo) {
        IPage ipage = customerChangeInfoService.findAllCustomerChangeInfo(page, customerEtcChangeInfo);
        return new RespR(ipage);
    }

    @PostMapping("/customerChangeInfo")
    @ApiOperation(value = "用户换卡信息查询", notes = "用户换卡信息查询")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR customerChangeInfo(@NotBlank(message = "申请Id不能为空") String applyId) {
        List<Map<String, String>> cards = customerChangeInfoService.selectChangeCards(applyId);
        return new RespR(cards);
    }


    /**
     * @param
     * @return
     */
    @PostMapping("/customeRecQueryList")
    @ApiOperation(value = "用户备案列表查询", notes = "用户备案列表查询")
    @LoginRequired(role = AuthenticationInterceptor.AUTH_ADMIN)
    public RespR customeRecQueryList() {
        return new RespR(customerRecService.findAllCustomeRecQueryList());
    }

}
