package com.crm.manager.controller;

import com.crm.manager.dto.export.AgentBalanceRecordExportDto;
import com.crm.manager.dto.export.AgentBalanceRecordExportEnDto;
import com.crm.manager.dto.export.AgentBalanceWithdrawaExportlDto;
import com.crm.manager.dto.export.IbInfoExportDto;
import com.crm.manager.entity.excel.AgentBalanceRecordExcelEntity;
import com.crm.manager.service.UserInfoService;
import com.crm.manager.service.ib.AgentBalanceRecordService;
import com.crm.manager.service.ib.IbInfoFeignService;
import com.crm.rely.backend.core.constant.Constants;
import com.crm.rely.backend.core.dto.base.BaseReportResultDto;
import com.crm.rely.backend.core.dto.base.BaseResultDto;
import com.crm.rely.backend.core.dto.base.BaseResultWithPagerDto;
import com.crm.rely.backend.core.dto.ib.balance.AgentBalanceRecordDto;
import com.crm.rely.backend.core.dto.ib.balance.AgentBalanceReportSumDto;
import com.crm.rely.backend.core.dto.ib.balance.AgentBalanceWithdrawalDto;
import com.crm.rely.backend.core.dto.ib.balance.AgentBalanceWithdrawalSumDto;
import com.crm.rely.backend.core.dto.ib.info.AgentInfoTreeDto;
import com.crm.rely.backend.core.dto.ib.info.IbInfoDto;
import com.crm.rely.backend.core.dto.ib.info.IbReportNewDto;
import com.crm.rely.backend.core.dto.ib.point.AgentPointDto;
import com.crm.rely.backend.core.dto.user.info.UserInfoIbNoDto;
import com.crm.rely.backend.core.entity.base.BaseIbReportListEntity;
import com.crm.rely.backend.core.entity.base.BaseValidEntity;
import com.crm.rely.backend.core.entity.base.SingleLongEntity;
import com.crm.rely.backend.core.entity.custom.info.CustomRegisterLinkCodeEntity;
import com.crm.rely.backend.core.entity.custom.info.InfoEntity;
import com.crm.rely.backend.core.entity.ib.balance.AgentBalanceRecordAddEntity;
import com.crm.rely.backend.core.entity.ib.info.*;
import com.crm.rely.backend.core.entity.ib.point.AgentPointSingleEntity;
import com.crm.rely.backend.core.entity.user.info.*;
import com.crm.rely.backend.util.EasyExcelUti;
import com.crm.rely.backend.util.ExportUtil;
import com.crm.rely.backend.util.FileProcessUtil;
import com.google.common.collect.Lists;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.util.StringUtils;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.Map;

/**
 * Created by max on 2020/7/14.
 */
@RestController
@RequestMapping("/ib")
public class IbInfoController {

    @Autowired
    private IbInfoFeignService ibInfoFeignService;
    @Autowired
    private AgentBalanceRecordService agentBalanceRecordService;
    @Autowired
    private UserInfoService userInfoService;

    @PostMapping("/search/single")
    public BaseResultDto<IbInfoDto> searchSingle(@RequestBody SingleLongEntity entity, InfoEntity infoEntity) throws Exception {
        return ibInfoFeignService.managerSearchSingle(entity);
    }


    @PostMapping("/search/ib/single")
    public BaseResultDto<UserInfoIbNoDto> searchIbSingle(@RequestBody UserInfoIbSearchEntity entity, InfoEntity infoEntity) throws Exception {
        return ibInfoFeignService.managerSearchIbSingle(entity);
    }

    @PostMapping("/search/list")
    public BaseResultWithPagerDto<List<IbInfoDto>> searchList(@RequestBody IbInfoSearchListEntity entity, InfoEntity infoEntity) throws Exception {
        return ibInfoFeignService.manageGetList(entity);
    }

    @GetMapping("/search/list/export")
    public void searchListExport(@RequestParam(name = "startDate") String startDate,
                                 @RequestParam(name = "endDate") String endDate,
                                 @RequestParam(name = "email") String email,
                                 @RequestParam(name = "ibNo") String ibNo,
                                 InfoEntity infoEntity, HttpServletResponse response) throws Exception {

        IbInfoSearchListEntity entity = new IbInfoSearchListEntity();
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyyMMdd");
        entity.setStartDate(startDate == null ? new Date() : simpleDateFormat.parse(startDate));
        entity.setEndDate(endDate == null ? new Date() : simpleDateFormat.parse(endDate));
        entity.setEmail(email);
        entity.setIbNo(ibNo);

        BaseResultDto<List<IbInfoDto>> resultDto = ibInfoFeignService.manageGetListExport(entity);
        if (resultDto.getCode() == Constants.SUCCESS_CODE) {
            List<IbInfoDto> dtos = resultDto.getData();
            List<IbInfoExportDto> exportDtos = Lists.newArrayList();
            dtos.forEach((item) -> {
                IbInfoExportDto exportDto = new IbInfoExportDto();
                BeanUtils.copyProperties(item, exportDto);
                exportDto.setCID(item.getCId());
                exportDto.setPIBNO(item.getPIbNo());
                exportDtos.add(exportDto);
            });
            ExportUtil.transferToResponse(FileProcessUtil.genExportFileName("IB_INFO_EXPORT"), exportDtos, IbInfoExportDto.class, response);

        }

    }

    @PostMapping("/delete/single")
    public BaseResultDto<Object> delete(@RequestBody SingleLongEntity entity, InfoEntity infoEntity) throws Exception {
        return ibInfoFeignService.deleteIbInSingle(entity);
    }

    @PostMapping("/update/hide")
    public BaseResultDto updateHide(@RequestBody @Validated UserInfoUpdateHideEntity entity) throws Exception {

        ibInfoFeignService.updateHide(entity);

        return BaseResultDto.success();
    }

    @PostMapping("/update/closeFunctions")
    public BaseResultDto<Object> updateCloseFunctions(@RequestBody UserInfoUpdateCloseFunctionsEntity entity) throws Exception {

        ibInfoFeignService.updateCloseFunctions(entity);

        return BaseResultDto.success();
    }

    @PostMapping("/update/commission/approval")
    public BaseResultDto updateCommissionApproval(@RequestBody @Validated UserInfoUpdateCommissionApprovalEntity entity) throws Exception {

        ibInfoFeignService.updateCommissionApproval(entity);

        return BaseResultDto.success();
    }

    @PostMapping("/update/login/group")
    public BaseResultDto updateSelectLoginTypeAndGroupType(@RequestBody @Validated UserInfoUpdateLoginTypeAndGroupTypeEntity entity) throws Exception {

        ibInfoFeignService.updateSelectLoginTypeAndGroupType(entity);

        return BaseResultDto.success();
    }

    @PostMapping("/update/show/login/type")
    public BaseResultDto updateExcludeShowLoginType(@RequestBody @Validated UserInfoUpdateExcludeShowLoginTypeEntity entity) throws Exception {

        ibInfoFeignService.updateExcludeShowLoginType(entity);

        return BaseResultDto.success();
    }

    /**
     * 新增代理报告
     *
     * @param entity
     * @param infoEntity
     * @return
     * @throws Exception
     */
    @PostMapping("/report/new")
    public BaseResultWithPagerDto<List<IbReportNewDto>> ibReportNew(@RequestBody IbReportNewEntity entity, InfoEntity infoEntity) throws Exception {
        entity.setStamp(null);
        return ibInfoFeignService.ibReportNew(entity);

    }

    /**
     * 代理和销售级联搜索树形结构
     *
     * @param entity
     * @param infoEntity
     * @return
     * @throws Exception
     */
    @PostMapping("/tree")
    public BaseResultDto<List<AgentInfoTreeDto>> getTree(@RequestBody AgentInfoTreeEntity entity, InfoEntity infoEntity) throws Exception {
        entity.setId(infoEntity.getIbInfo().getId());
        entity.setStamp(infoEntity.getIbInfo().getStamp());
        if (entity.getPid() == null || entity.getPid() <= 0) {
            entity.setPid(entity.getId());
        }
        return ibInfoFeignService.getTree(entity);
    }

    @PostMapping("/tree/search")
    public BaseResultDto<List<AgentInfoTreeDto>> agentTreeSearch(@RequestBody AgentInfoTreeEntity entity, InfoEntity infoEntity) throws Exception {
        entity.setStamp(infoEntity.getIbInfo().getStamp());

        return ibInfoFeignService.agentTreeSearch(entity);
    }

    /**
     * 余额操作报告
     *
     * @param entity
     * @param infoEntity
     * @return
     * @throws Exception
     */
    @PostMapping("/report/balance")
    public BaseReportResultDto<List<AgentBalanceRecordDto>, AgentBalanceReportSumDto> ibBalanceReport(@RequestBody BaseIbReportListEntity entity, InfoEntity infoEntity) throws Exception {
        return ibInfoFeignService.ibBalanceReport(entity);
    }

    /**
     * 余额操作报告导出
     *
     * @param startDate
     * @param endDate
     * @param infoEntity
     * @param response
     * @throws Exception
     */
    @GetMapping("/report/balance/export")
    public void ibBalanceReportExport(@RequestParam(name = "startDate") String startDate,
                                      @RequestParam(name = "endDate") String endDate,
                                      @RequestParam(name = "lang") String lang,
                                      InfoEntity infoEntity, HttpServletResponse response) throws Exception {

        BaseIbReportListEntity entity = new BaseIbReportListEntity();
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyyMMdd");
        entity.setStartDate(startDate == null ? new Date() : simpleDateFormat.parse(startDate));
        entity.setEndDate(endDate == null ? new Date() : simpleDateFormat.parse(endDate));

        BaseResultDto<List<AgentBalanceRecordDto>> resultDto = ibInfoFeignService.ibBalanceReportExport(entity);
        if (resultDto.getCode() == Constants.SUCCESS_CODE) {
            if (StringUtils.isEmpty(lang) || "cn".equalsIgnoreCase(lang)) {
                List<AgentBalanceRecordDto> dtos = resultDto.getData();
                List<AgentBalanceRecordExportDto> exportDtos = Lists.newArrayList();
                dtos.forEach((item) -> {
                    AgentBalanceRecordExportDto exportDto = new AgentBalanceRecordExportDto();
                    BeanUtils.copyProperties(item, exportDto);
                    exportDtos.add(exportDto);
                });

                ExportUtil.transferToResponse(FileProcessUtil.genExportFileName("IB_BALANCE_EXPORT"), exportDtos, AgentBalanceRecordExportDto.class, response);
            } else {
                List<AgentBalanceRecordDto> dtos = resultDto.getData();
                List<AgentBalanceRecordExportEnDto> exportDtos = Lists.newArrayList();
                dtos.forEach((item) -> {
                    AgentBalanceRecordExportEnDto exportDto = new AgentBalanceRecordExportEnDto();
                    BeanUtils.copyProperties(item, exportDto);
                    exportDtos.add(exportDto);
                });

                ExportUtil.transferToResponse(FileProcessUtil.genExportFileName("IB_BALANCE_EXPORT"), exportDtos, AgentBalanceRecordExportEnDto.class, response);
            }

        }

    }

    /**
     * 代理佣金取款报告
     *
     * @param entity
     * @param infoEntity
     * @return
     * @throws Exception
     */
    @PostMapping("/report/withdrawal")
    public BaseReportResultDto<List<AgentBalanceWithdrawalDto>, AgentBalanceWithdrawalSumDto> ibWithdrawalReport(@RequestBody BaseIbReportListEntity entity, InfoEntity infoEntity) throws Exception {
        return ibInfoFeignService.ibWithdrawalReport(entity);
    }

    @GetMapping("/report/withdrawal/export")
    public void ibWithdrawalReporteExport(
                @RequestParam(name = "startDate") String startDate,
                @RequestParam(name = "endDate") String endDate,
                @RequestParam(name = "agentId") Long agentId,
                @RequestParam(name = "cId") Long cId,
                HttpServletResponse response) throws Exception {
        SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyyMMdd");
        BaseIbReportListEntity entity = new BaseIbReportListEntity();
        entity.setStartDate(startDate == null ? new Date() : simpleDateFormat.parse(startDate));
        entity.setEndDate(endDate == null ? new Date() : simpleDateFormat.parse(endDate));
        entity.setAgentId(agentId);
        entity.setCId(cId);
        BaseResultDto<List<AgentBalanceWithdrawalDto>> resultDto = ibInfoFeignService.ibWithdrawalReporteExport(entity);

        if (resultDto.getCode() == Constants.SUCCESS_CODE) {
            List<AgentBalanceWithdrawalDto> dtos = resultDto.getData();
            List<AgentBalanceWithdrawaExportlDto> exportDtos = Lists.newArrayList();
            dtos.forEach((item) -> {
                AgentBalanceWithdrawaExportlDto exportDto = new AgentBalanceWithdrawaExportlDto();
                BeanUtils.copyProperties(item, exportDto);
                exportDto.setCID(item.getCId());
                exportDtos.add(exportDto);
            });

            ExportUtil.transferToResponse(FileProcessUtil.genExportFileName("IB_BALANCE_EXPORT"), exportDtos, AgentBalanceWithdrawaExportlDto.class, response);


        }
    }

    /**
     * 代理返点信息
     *
     * @param entity
     * @param infoEntity
     * @return
     * @throws Exception
     */
    @PostMapping("/point")
    public BaseResultDto<AgentPointDto> ibPoint(@RequestBody AgentPointSingleEntity entity, InfoEntity infoEntity) throws Exception {
        return ibInfoFeignService.ibPoint(entity);
    }

    /**
     * 修改代理是否可申请pamm manager
     *
     * @param entity
     * @return
     * @throws Exception
     */
    @PostMapping("/update/pammManagerValid")
    public BaseResultDto<Object> updatePammManagerValid(@RequestBody @Validated UserInfoUpdatePammManagerValidEntity entity) throws Exception {
        if (entity.getPammManagerValid() == null || entity.getPammManagerValid() <= 0) {
            entity.setPammManagerValid(0);
        } else {
            entity.setPammManagerValid(1);
        }

        return ibInfoFeignService.updatePammManagerValid(entity);

    }

    /**
     * 修改代理是否可申请pamm(老的PAMM)
     *
     * @param entity
     * @return
     * @throws Exception
     */
    @PostMapping("/update/pammValid")
    public BaseResultDto<Object> updatePammValid(@RequestBody @Validated UserInfoUpdatePammValidEntity entity) throws Exception {
        if (entity.getPammValid() == null || entity.getPammValid() <= 0) {
            entity.setPammValid(0);
        } else {
            entity.setPammValid(1);
        }

        return ibInfoFeignService.updatePammValid(entity);

    }

    /**
     * 批量导出代理余额操作
     *
     * @param file
     * @param req
     * @param infoEntity
     * @return
     * @throws Exception
     */
    @PostMapping("/upload/balance/record")
    public BaseResultDto upload(@RequestParam(value = "file", required = false) MultipartFile file,
                                HttpServletRequest req,
                                InfoEntity infoEntity) throws Exception {
        List<AgentBalanceRecordExcelEntity> entities = EasyExcelUti.readExcel(file,
                new AgentBalanceRecordExcelEntity(), 1, AgentBalanceRecordExcelEntity.class);

        if (entities == null || entities.size() <= 0) {
            return BaseResultDto.success();
        }

        List<String> ibNos = Lists.newArrayList();
        for (AgentBalanceRecordExcelEntity entity : entities) {
            ibNos.add(entity.getIbNo());
        }

        Map<String, Long> map = userInfoService.mapIdByIbNo(ibNos);

        List<AgentBalanceRecordAddEntity> importEntities = Lists.newArrayList();
        Date now = new Date();
        for (AgentBalanceRecordExcelEntity entity : entities) {
            if (map.get(entity.getIbNo()) == null
                    || entity.getAmount() == null
                    || StringUtils.isEmpty(entity.getType())
                    || StringUtils.isEmpty(entity.getBalanceType())) {
                continue;
            }

            AgentBalanceRecordAddEntity importEntity = new AgentBalanceRecordAddEntity();
            importEntity.setAddTime(now);
            importEntity.setAddUser(infoEntity.getIbInfo().getId());
            importEntity.setAgentId(map.get(entity.getIbNo()));
            importEntity.setAmount(entity.getAmount());
            importEntity.setComment(entity.getComment());

            if ("INCREASE".equalsIgnoreCase(entity.getType())) {
                importEntity.setType(1);
            } else if ("DECREASE".equalsIgnoreCase(entity.getType())) {
                importEntity.setType(2);
            }


            if ("REBATE".equalsIgnoreCase(entity.getBalanceType())) {
                importEntity.setBalanceType(1);
            } else if ("COMMISSION".equalsIgnoreCase(entity.getBalanceType())) {
                importEntity.setBalanceType(2);
            } else if ("FOLLOW_COMMISSION".equalsIgnoreCase(entity.getBalanceType())) {
                importEntity.setBalanceType(2);
            }

            importEntities.add(importEntity);

        }

        return agentBalanceRecordService.batchAdd(importEntities);
    }

    @PostMapping("/register/link/hash")
    public BaseResultDto<String> getLinkHash(@RequestBody CustomRegisterLinkCodeEntity entity) throws Exception {
        return ibInfoFeignService.getLinkValue(entity);
    }

    @PostMapping("/agent/setting")
    public BaseResultDto ibAgentAccountSetting(@RequestBody IbAccountSettingEntity entity) throws Exception {
        return ibInfoFeignService.ibAgentAccountSetting(entity);
    }

    @PostMapping("/fixed/hide")
    public BaseResultDto ibAgentFixedHide(@RequestBody IbFixedHideEntity entity) throws Exception {
        return ibInfoFeignService.ibAgentFixedHide(entity);
    }

    @PostMapping("/agent/transfer")
    public BaseResultDto ibAgentTransfer(@RequestBody IbAgentTansferEntity entity) throws Exception {
        return ibInfoFeignService.ibAgentTransfer(entity);
    }

    /**
     * 控制代理佣金
     * @param entity
     * @param infoEntity
     * @return
     * @throws Exception
     */
    @PostMapping("/commission/valid")
    public BaseResultDto<Object> commissionValid(@RequestBody BaseValidEntity entity, InfoEntity infoEntity) throws Exception {
        return ibInfoFeignService.commissionValid(entity);
    }

    @PostMapping("/search/all")
    public BaseResultDto<List<AgentInfoTreeDto>> searchAllAgentInfo(@RequestBody AgentInfoTreeEntity entity) throws Exception {
        return ibInfoFeignService.searchAllAgentInfo(entity);
    }


}
