package com.fs.his.controller;

import cn.hutool.core.bean.BeanUtil;
import cn.hutool.core.util.StrUtil;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.fs.common.annotation.Log;
import com.fs.common.core.controller.BaseController;
import com.fs.common.core.domain.AjaxResult;
import com.fs.common.core.domain.R;
import com.fs.common.core.page.TableDataInfo;
import com.fs.common.enums.BusinessType;
import com.fs.common.utils.CloudHostUtils;
import com.fs.common.utils.StringUtils;
import com.fs.common.utils.poi.ExcelUtil;
import com.fs.his.domain.FsDfAccount;
import com.fs.his.domain.FsIntegralOrder;
import com.fs.his.domain.FsIntegralOrderDf;
import com.fs.his.domain.FsStoreOrder;
import com.fs.his.dto.ExpressInfoDTO;
import com.fs.his.enums.ShipperCodeEnum;
import com.fs.his.mapper.FsIntegralOrderMapper;
import com.fs.his.param.BatchCreateErpOrderParam;
import com.fs.his.param.BatchSetErpOrderParam;
import com.fs.his.vo.*;
import com.fs.his.param.FsIntegralOrderParam;
import com.fs.his.service.*;
import com.fs.utils.OrderContextHolder;
import io.swagger.annotations.ApiOperation;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.text.ParseException;
import java.time.LocalDateTime;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;

import static com.fs.his.utils.PhoneUtil.decryptAutoPhoneMk;
import static com.fs.his.utils.PhoneUtil.decryptPhone;

/**
 * 积分商品订单Controller
 *
 * @author fs
 * @date 2023-11-02
 */
@RestController
@RequestMapping("/his/integralOrder")
public class FsIntegralOrderController extends BaseController
{
    @Autowired
    private IFsIntegralOrderService fsIntegralOrderService;
    @Autowired
    private IFsExpressService expressService;

    @Autowired
    private IFsStoreOrderService fsStoreOrderService;


    @Autowired
    private IFsIntegralOrderDfService integralOrderDfService;

    @Autowired
    private IFsDfAccountService fsDfAccountService;
    @Autowired
    private FsIntegralOrderMapper integralOrderMapper;
    @Autowired
    private FsIntegralOrderMapper fsIntegralOrderMapper;

    /**
     * 查询积分商品订单列表
     */
    @PreAuthorize("@ss.hasPermi('his:integralOrder:list')")
    @GetMapping("/list")
    public TableDataInfo list(FsIntegralOrderParam fsIntegralOrder)
    {
        startPage();
        if (CloudHostUtils.hasCloudHostName("金牛明医")){
            /*目前只有金牛有状态为6的查询，其他项目避免使用6状态码*/
            if (fsIntegralOrder.getStatus() != null && fsIntegralOrder.getStatus().equals("6")) {
                fsIntegralOrder.setStatus("1");
                fsIntegralOrder.setIsPush(0);
            }
            List<FsIntegralOrderListVO> list = fsIntegralOrderService.selectFsIntegralOrderListByJn(fsIntegralOrder);
            for (FsIntegralOrderListVO vo : list) {
                vo.setUserPhone(decryptAutoPhoneMk(vo.getUserPhone()));
            }
            return getDataTable(list);
        }
        List<FsIntegralOrderListVO> list = fsIntegralOrderService.selectFsIntegralOrderListVO(fsIntegralOrder);
        for (FsIntegralOrderListVO vo : list) {
            vo.setUserPhone(decryptAutoPhoneMk(vo.getUserPhone()));
        }
        return getDataTable(list);
    }

    /**
     * 导出积分商品订单列表
     */
    @PreAuthorize("@ss.hasPermi('his:integralOrder:export')")
    @Log(title = "积分商品订单", businessType = BusinessType.EXPORT)
    @GetMapping("/export")
    public AjaxResult export(FsIntegralOrder fsIntegralOrder)
    {
        if (CloudHostUtils.hasCloudHostName("金牛明医")&&fsIntegralOrder.getStatus() != null && fsIntegralOrder.getStatus().equals(6)) {
            /*目前只有金牛有状态为6的查询，其他项目避免使用6状态码*/
            FsIntegralOrderParam param = new FsIntegralOrderParam();
            BeanUtil.copyProperties(fsIntegralOrder, param);
            param.setStatus("1");
            param.setIsPush(0);
            List<FsIntegralOrderListVO> fsIntegralOrderListVOS = fsIntegralOrderService.selectFsIntegralOrderListByJn(param);
            ExcelUtil<FsIntegralOrderListVO> util = new ExcelUtil<>(FsIntegralOrderListVO.class);
            return util.exportExcel(new ArrayList<>(fsIntegralOrderListVOS), "积分商品订单数据");
        }
        return fsIntegralOrderService.export(fsIntegralOrder);
    }
    /**
     * 发货
     */
    @PreAuthorize("@ss.hasPermi('his:integralOrder:sendGoods')")
    @PutMapping("/sendGoods")
    public AjaxResult sendGoods(@RequestBody FsIntegralOrder fsIntegralOrder)
    {
        return toAjax(fsIntegralOrderService.sendGoods(fsIntegralOrder));
    }

    @GetMapping("/importTemplate")
    public AjaxResult sendExport()
    {
        ExcelUtil<FsStoreProductDeliverExcelVO> util = new ExcelUtil<>(FsStoreProductDeliverExcelVO.class);
        return util.importTemplateExcel("导入运单号");
    }
    @Log(title = "导入运单号", businessType = BusinessType.IMPORT)
    @PostMapping("/importData")
    public AjaxResult importData(MultipartFile file, boolean updateSupport) throws Exception
    {
        ExcelUtil<FsStoreProductDeliverExcelVO> util = new ExcelUtil<>(FsStoreProductDeliverExcelVO.class);
        List<FsStoreProductDeliverExcelVO> list = util.importExcel(file.getInputStream());
        String message = fsIntegralOrderService.importProductDeliver(list);
        return AjaxResult.success(message);
    }
    @PreAuthorize("@ss.hasPermi('his:integralOrder:express')")
    @GetMapping(value = "/getExpress/{id}")
    public R getExpress(@PathVariable("id") Long id)
    {
        /**
         * selectFsIntegralOrderByOrderId查询的数据表:fs_integral_order
         * 需要执行添加字段的DDL语句
         * ALTER TABLE `fs_integral_order`
         * ADD COLUMN `login_account` VARCHAR(20) CHARACTER SET utf8 COLLATE utf8_unicode_ci DEFAULT NULL COMMENT '代服物流查询账号';
         * */
        FsIntegralOrder fsIntegralOrder = fsIntegralOrderService.selectFsIntegralOrderByOrderId(id);
        ExpressInfoDTO expressInfoDTO=null;
        //代服管家 查询自己的物流
        if (CloudHostUtils.hasCloudHostName("金牛明医")) {
            FsStoreOrder fsStoreOrder = new FsStoreOrder();
            fsStoreOrder.setOrderCode(fsIntegralOrder.getOrderCode());
            //线程携带订单信息
            OrderContextHolder.setIntegralOrder(fsIntegralOrder);
            expressInfoDTO = fsStoreOrderService.getDfExpressInfoDTO(fsStoreOrder);
        }else {
            if (StringUtils.isNotEmpty(fsIntegralOrder.getDeliverySn())) {
                String lastFourNumber = "";
                if (fsIntegralOrder.getDeliveryCode().equals(ShipperCodeEnum.SF.getValue())) {

                    lastFourNumber = fsIntegralOrder.getUserPhone();
                    if (lastFourNumber.length() == 11) {
                        lastFourNumber = StrUtil.sub(lastFourNumber, lastFourNumber.length(), -4);
                    }
                }
                expressInfoDTO = expressService.getExpressInfo(fsIntegralOrder.getOrderCode(), fsIntegralOrder.getDeliveryCode(), fsIntegralOrder.getDeliverySn(), lastFourNumber);
            }
        }
        return R.ok().put("data",expressInfoDTO);
    }
    /**
     * 获取积分商品订单详细信息
     */
    @PreAuthorize("@ss.hasPermi('his:integralOrder:query')")
    @GetMapping(value = "/{orderId}")
    public AjaxResult getInfo(@PathVariable("orderId") Long orderId)
    {
        FsIntegralOrderPVO order = fsIntegralOrderService.selectFsIntegralOrderPVO(orderId);

        order.setUserPhone(decryptAutoPhoneMk(order.getUserPhone()));
        return AjaxResult.success(order);
    }

    @GetMapping(value = "/queryPhone/{orderId}")
    @Log(title = "积分订单电话", businessType = BusinessType.GRANT)
    @PreAuthorize("@ss.hasPermi('his:integralOrder:queryPhone')")
    public R getPhone(@PathVariable("orderId") Long orderId)
    {
        FsIntegralOrderPVO order = fsIntegralOrderService.selectFsIntegralOrderPVO(orderId);
        String userPhone = order.getUserPhone();
        if (userPhone.length()>11){
            userPhone = decryptPhone(userPhone);
        }
        return R.ok().put("userPhone",userPhone);
    }

    /**
     * 新增积分商品订单
     */
    @PreAuthorize("@ss.hasPermi('his:integralOrder:add')")
    @Log(title = "积分商品订单", businessType = BusinessType.INSERT)
    @PostMapping
    public AjaxResult add(@RequestBody FsIntegralOrder fsIntegralOrder)
    {
        return toAjax(fsIntegralOrderService.insertFsIntegralOrder(fsIntegralOrder));
    }

    /**
     * 修改积分商品订单
     */
    @PreAuthorize("@ss.hasPermi('his:integralOrder:edit')")
    @Log(title = "积分商品订单", businessType = BusinessType.UPDATE)
    @PutMapping
    public AjaxResult edit(@RequestBody FsIntegralOrder fsIntegralOrder)
    {
        return toAjax(fsIntegralOrderService.updateFsIntegralOrder(fsIntegralOrder));
    }

    /**
     * 删除积分商品订单
     */
    @PreAuthorize("@ss.hasPermi('his:integralOrder:remove')")
    @Log(title = "积分商品订单", businessType = BusinessType.DELETE)
	@DeleteMapping("/{orderIds}")
    public AjaxResult remove(@PathVariable Long[] orderIds)
    {
        return toAjax(fsIntegralOrderService.deleteFsIntegralOrderByOrderIds(orderIds));
    }
    @PreAuthorize("@ss.hasPermi('his:integralOrder:cancel')")
    @Log(title = "积分商品订单", businessType = BusinessType.UPDATE)
    @PostMapping("/cancelOrder")
    public AjaxResult cancelOrder(@RequestBody Map<String, String> requestBody){
        String orderCode = requestBody.get("orderCode");
        return toAjax(fsIntegralOrderService.cancelOrder(orderCode));
    }
    /**
     * 申请退款
     * 接口不校验是否发货
     * */
    @PreAuthorize("@ss.hasPermi('his:integralOrder:cancel')")
    @Log(title = "积分商品订单", businessType = BusinessType.UPDATE)
    @PostMapping("/mandatoryRefunds")
    public AjaxResult mandatoryRefunds(@RequestBody Map<String, String> requestBody){
        String orderCode = requestBody.get("orderCode");
        return toAjax(fsIntegralOrderService.mandatoryRefunds(orderCode));
    }

    /**
     * 确认收货
     * todo:权限标识符待定
     */
    @Log(title = "积分商品订单", businessType = BusinessType.UPDATE)
    @GetMapping("/finishOrder/{orderCode}")
    public AjaxResult finishOrder(@PathVariable("orderCode") String orderCode) {
        return toAjax(fsIntegralOrderService.finishOrder(orderCode));
    }

    @ApiOperation("批量设置订单账户")
    @Log(title = "积分商品订单", businessType = BusinessType.UPDATE)
//    @PreAuthorize("@ss.hasPermi('his:storeOrder:createErpOrder')")
    @PostMapping(value = "/batchSetErpOrder")
    @Transactional(rollbackFor = Exception.class)
    public R batchSetErpOrder(@RequestBody BatchSetErpOrderParam param)
    {
        String nickName = getLoginUser().getUser().getNickName();
        String loginAccount = param.getLoginAccount();
        if (StringUtils.isBlank(loginAccount)){
            return R.error("未选择erp账户");
        }
        FsIntegralOrderDf df = getDFInfo(loginAccount);
        if (df.getLoginAccount() == null){
            return R.error("未查询到所选erp账户");
        }
        List<Long> orderIds = param.getOrderIds();
        List<FsIntegralOrder> list = null;
        if (!orderIds.isEmpty()) {
            list = fsIntegralOrderService.selectFsIntegralOrderByOrderIds(orderIds);
//            orderIds = list.stream().map(FsIntegralOrder::getOrderId).collect(Collectors.toList());
        }else{
            return R.ok();
        }
        if (list.isEmpty())
            return R.ok();
        List<String> erpPhones = param.getErpPhones();
        int[] index = {0}; // 使用数组模拟可变引用
        list.forEach(item->{
            df.setOrderId(item.getOrderId());
            df.setOrderCode(item.getOrderCode());
            if (!erpPhones.isEmpty()) {
                int currentIndex = index[0] % erpPhones.size(); // 循环使用
                df.setErpPhone(erpPhones.get(currentIndex));
                index[0]++; // 顺序递增
            }
            FsIntegralOrder order = new FsIntegralOrder();
            //更新一下积分订单的loginaccount这个字段
            order.setOrderId(item.getOrderId());
            order.setLoginAccount(df.getLoginAccount());
//            fsIntegralOrderService.updateFsIntegralOrder(order);
            fsIntegralOrderMapper.updateById(order);
            FsIntegralOrderDf temp = integralOrderDfService.getOne(Wrappers.<FsIntegralOrderDf>lambdaQuery().eq(FsIntegralOrderDf::getOrderId,item.getOrderId()));
            df.setParcelQuantity(param.getParcelQuantity());
//            df.setErpPhone(param.getErpPhone().trim());
            if (temp != null){
                df.setUpdateTime(LocalDateTime.now());
                integralOrderDfService.updateById(df);
            } else {
                integralOrderDfService.insertFsIntegralOrderDf(df);
            }
            //积分订单操作日志暂定
        });
        return R.ok();
    }

//    @Log(title = "手动推管易", businessType = BusinessType.INSERT)
    @ApiOperation("批量创建ERP订单")
//    @PreAuthorize("@ss.hasPermi('his:storeOrder:createErpOrder')")
    @Log(title = "积分商品订单", businessType = BusinessType.UPDATE)
    @PostMapping(value = "/batchCreateErpOrder")
    public R batchCreateErpOrder(@RequestBody BatchCreateErpOrderParam param) throws ParseException {
//        String nickName = getLoginUser().getUser().getNickName();
        String loginAccount = param.getLoginAccount();
        if (StringUtils.isBlank(loginAccount)){
            return R.error("未选择推送erp账户");
        }
        FsIntegralOrderDf df = getDFInfo(loginAccount);
        if (df.getLoginAccount() == null){
            return R.error("未查询到所选erp账户");
        }
        List<Long> orderIds = param.getOrderIds();
        List<String> erpPhones = param.getErpPhones();
        int[] index = {0}; // 使用数组模拟可变引用
        if (!orderIds.isEmpty()) {
            List<FsIntegralOrder> orders = integralOrderMapper.selectList(Wrappers.<FsIntegralOrder>lambdaQuery().in(FsIntegralOrder::getOrderId, orderIds));
            for (FsIntegralOrder order : orders) {
                df.setOrderId(order.getOrderId());
                df.setOrderCode(order.getOrderCode());
                FsIntegralOrderDf temp = integralOrderDfService.getBaseMapper().selectById(order.getOrderId());
                //如果是没有代服表数据，就用传过来的df账号，如果有就不更新df数据直接拿之前的数据创建erp
                if (temp == null){
                    if (!erpPhones.isEmpty()) {
                        int currentIndex = index[0] % erpPhones.size(); // 循环使用
                        df.setErpPhone(erpPhones.get(currentIndex));
                        index[0]++; // 顺序递增
                    }
                    df.setParcelQuantity(param.getParcelQuantity()); //设置包裹数量
                    integralOrderDfService.getBaseMapper().insert(df);
                    order.setLoginAccount(df.getLoginAccount());
                    integralOrderMapper.updateById(order);
                    //日志表，待定
                }
                fsIntegralOrderService.createErpOrder(order.getOrderId());
            }
        }
        return R.ok("推送成功");
    }

    @Log(title = "导入修改订单", businessType = BusinessType.IMPORT)
    @PostMapping("/importOrderStatusData")
    public AjaxResult importOrderStatusData(MultipartFile file) throws Exception
    {
        ExcelUtil<FsIntegralOrderExcelVO> util = new ExcelUtil<>(FsIntegralOrderExcelVO.class);
        List<FsIntegralOrderExcelVO> list = util.importExcel(file.getInputStream());
        String message = fsIntegralOrderService.importOrderStatusData(list);
        return AjaxResult.success(message);
    }

    @GetMapping("/importUpdateOrderTemplate")
    public AjaxResult importUpdateOrderTemplate()
    {
        ExcelUtil<FsIntegralOrderExcelVO> util = new ExcelUtil<>(FsIntegralOrderExcelVO.class);
        return util.importTemplateExcel("修改订单");
    }
    private FsIntegralOrderDf getDFInfo(String loginAccount) {
        //查询订单账户 判断是否存在该订单账户
        FsDfAccount erpAccount = fsDfAccountService.selectFsDfAccountByAccount(loginAccount);
        FsIntegralOrderDf df = new FsIntegralOrderDf();
        if (erpAccount != null){
            //添加df记录
            df.setAppKey(erpAccount.getDfAppKey());
            df.setAppSecret(erpAccount.getDfAppsecret());
            df.setLoginAccount(loginAccount);
            df.setMonthlyCard(erpAccount.getMonthlyCard());
            df.setExpressProductCode(erpAccount.getExpressProductCode());
            df.setStatus(0);
        }
        return df;
    }
}
