package com.cyksj.web.controller.manage.register;

import cn.dev33.satoken.annotation.SaCheckPermission;
import cn.hutool.core.date.DateTime;
import cn.hutool.core.util.StrUtil;
import com.alibaba.excel.EasyExcel;
import com.alibaba.excel.support.ExcelTypeEnum;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.cyksj.common.exception.BusinessRuntimeException;
import com.cyksj.common.util.IoKit;
import com.cyksj.common.util.Xmls;
import com.cyksj.dto.Result;
import com.cyksj.enums.GatewayResponse;
import com.cyksj.mapper.AppleAutoRegisterDataMapper;
import com.cyksj.mapper.SpotifyUnLimitRecordMapper;
import com.cyksj.model.entity.AppleAutoRegisterData;
import com.cyksj.model.entity.RegisterOrderDon;
import com.cyksj.model.entity.SpotifyUnLimitRecord;
import com.cyksj.model.excel.ExcelAppleIdTemplateData;
import com.cyksj.model.excel.listener.ExcelAppleDataListener;
import com.cyksj.model.request.OrderRefundReq;
import com.cyksj.model.views.AppleIdCountryOrAreaDataView;
import com.cyksj.model.views.AppleIdHeadDataView;
import com.cyksj.model.views.AppleIdRegisterView;
import com.cyksj.service.mange.SpotifySendMsgService;
import com.cyksj.service.register.RegisterOrderDonService;
import com.cyksj.web.util.EasyExcelUtils;
import com.ejlchina.searcher.BeanSearcher;
import com.ejlchina.searcher.SearchResult;
import com.ejlchina.searcher.param.Operator;
import com.ejlchina.searcher.util.MapBuilder;
import com.ejlchina.searcher.util.MapUtils;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
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.io.OutputStream;
import java.util.Map;

/**
 * @author chan
 * @date 2022/11/7 1:49 PM
 */
@Slf4j
@RestController
@RequestMapping("/manage/register")
@RequiredArgsConstructor
public class CmsRegisterController {

    private final RegisterOrderDonService registerOrderDonService;

    private final BeanSearcher beanSearcher;

    private final HttpServletRequest request;

    private final AppleAutoRegisterDataMapper appleAutoRegisterDataMapper;

    private final SpotifyUnLimitRecordMapper spotifyUnLimitRecordMapper;

    private final SpotifySendMsgService spotifySendMsgService;

    @GetMapping("/get")
    @SaCheckPermission("sign:view")
    public Result<SearchResult<RegisterOrderDon>> get(Boolean appleIsAutoType) {
        MapBuilder builder = MapUtils.flatBuilder(request.getParameterMap());
        if (appleIsAutoType != null) {
            if (appleIsAutoType) {
                builder.field(RegisterOrderDon::getAppleAutoId).op(Operator.NotNull);
            }else {
                builder.field(RegisterOrderDon::getAppleAutoId).op(Operator.IsNull);
            }
        }
        SearchResult<RegisterOrderDon> search = beanSearcher.search(RegisterOrderDon.class, builder.build());
        search.getDataList().forEach(data->{
            if (data.getAppleIsAutoType()) {
                data.setCountry(data.getCountryOrArea().getDesc());
                data.setEmail(data.getApplePwdId());
            }
        });
        return GatewayResponse.SUCCESS.newBuilder().toResult(search);
    }

    @PutMapping("/update")
    public Result<RegisterOrderDon> update(@RequestBody RegisterOrderDon registerOrderDon){
        registerOrderDonService.updateById(registerOrderDon);
        return GatewayResponse.SUCCESS.newBuilder().toResult(registerOrderDon);
    }

    /**
     * 下载apple id 导入模板
     */
    @GetMapping("/get/appleId/template")
    public void appleIdTemplate(HttpServletResponse response) {
        EasyExcelUtils.createTemplateExcel(response, ExcelAppleIdTemplateData.class, "导入模板", "导入模板", ExcelTypeEnum.XLSX, null);
    }

    /**
     * 导入apple Id注册数据
     */
    @PostMapping("/export/appleId/data")
    public Result<String> exportRegisterAppleData(MultipartFile file, String remark, String countryOrArea) throws Exception {
        EasyExcel.read(file.getInputStream(), ExcelAppleIdTemplateData.class, new ExcelAppleDataListener(appleAutoRegisterDataMapper, countryOrArea, remark)).sheet().doRead();
        return GatewayResponse.SUCCESS.newBuilder().toResult("导入数据成功");
    }

    /**
     * apple ID注册数据列表
     */
    @GetMapping("/get/appleId/list")
    public Result<SearchResult<AppleIdRegisterView>> getAppleIdList(HttpServletRequest request) {
        return GatewayResponse.SUCCESS.newBuilder().toResult(beanSearcher.search(AppleIdRegisterView.class, MapUtils.flatBuilder(request.getParameterMap()).build()));
    }

    /**
     * apple ID头部数据
     */
    @GetMapping("/get/appleId/head")
    public Result<AppleIdHeadDataView> getAppleIdHeadDataView() {
        AppleIdCountryOrAreaDataView appleIdCountryOrAreaDataView = new AppleIdCountryOrAreaDataView();
        appleIdCountryOrAreaDataView.setJapanAvaNum(appleAutoRegisterDataMapper.selectAreaDataView(AppleAutoRegisterData.CountryOrArea.JAPAN));
        appleIdCountryOrAreaDataView.setHongKongAvaNum(appleAutoRegisterDataMapper.selectAreaDataView(AppleAutoRegisterData.CountryOrArea.CN_HongKong));
        appleIdCountryOrAreaDataView.setUsAvaNum(appleAutoRegisterDataMapper.selectAreaDataView(AppleAutoRegisterData.CountryOrArea.US));
        appleIdCountryOrAreaDataView.setTaiWanAvaNum(appleAutoRegisterDataMapper.selectAreaDataView(AppleAutoRegisterData.CountryOrArea.CN_TaiWan));
        AppleIdHeadDataView appleIdHeadDataView = new AppleIdHeadDataView();
        appleIdHeadDataView.setAreaDataView(appleIdCountryOrAreaDataView);
        Integer avaAppleIdNum = appleAutoRegisterDataMapper.selectCount(Wrappers.lambdaQuery(AppleAutoRegisterData.class).eq(AppleAutoRegisterData::getStatus, false));
        appleIdHeadDataView.setAvaAppleIdNum(avaAppleIdNum);
        Integer usedAppleIdNum = appleAutoRegisterDataMapper.selectCount(Wrappers.lambdaQuery(AppleAutoRegisterData.class).eq(AppleAutoRegisterData::getStatus, true));
        appleIdHeadDataView.setUsedAppleIdNum(usedAppleIdNum);
        return GatewayResponse.SUCCESS.newBuilder().toResult(appleIdHeadDataView);
    }
    /**
     * 微信订单退款
     */
    @PostMapping("/wx/refund")
    @SaCheckPermission("sign:refund")
    public Result<String> wxRefund(@RequestBody @Validated OrderRefundReq refundReq) throws Exception {
        RegisterOrderDon registerOrderDon = registerOrderDonService.getById(refundReq.getOrderId());
        if (registerOrderDon==null) throw BusinessRuntimeException.getInstance("");
        return registerOrderDonService.wxRefund(refundReq, registerOrderDon);
    }

    /**
     * 微信退款回调
     */
    @PostMapping("/wx/refund/notify")
    public void wxRefundNotify(HttpServletRequest request, HttpServletResponse response) throws Exception {
        String xml = IoKit.toString(request.getInputStream());
        log.info("=== 注册账号退款成功的回调: \n {}", xml);

        // 解析xml
        Map<String, String> map = Xmls.toMap(xml);

        // 退款失败
        if (!StrUtil.equals("SUCCESS", map.get("return_code"))) {
            throw BusinessRuntimeException.getInstance("退款失败.");
        }

        registerOrderDonService.wxRefundNotify(map);

        String toWechatXmlResponse = "<xml><return_code><![CDATA[SUCCESS]]></return_code><return_msg><![CDATA[OK]]></return_msg></xml>";

        OutputStream out = null;
        try {
            out = response.getOutputStream();
            IoKit.write(toWechatXmlResponse, out);
        } catch (Throwable e) {
            throw BusinessRuntimeException.getInstance(e == null ? null : e.getMessage());
        } finally {
            IoKit.close(out);
        }
    }

    /**
     * 注册 统一退款
     */
    @PostMapping("/unified/refund")
    public Result<String> unifiedRefund(@RequestBody OrderRefundReq refundReq) throws Exception {
        registerOrderDonService.unifiedRefund(refundReq);
        return GatewayResponse.SUCCESS.newBuilder().toResult();
    }

    /**
     * 获取需要解除限制的账号列表
     */
    @GetMapping("/unLimit")
    public Result<SearchResult<SpotifyUnLimitRecord>> getUnLimit(){
        SearchResult<SpotifyUnLimitRecord> search = beanSearcher.search(SpotifyUnLimitRecord.class, MapUtils.flatBuilder(request.getParameterMap())
                .field(SpotifyUnLimitRecord::getStatus,"Processing").build());
        return GatewayResponse.SUCCESS.newBuilder().toResult(search);
    }

    /**
     * 修改解除限制状态
     */
    @PutMapping("/unLimit")
    public Result<String> upUnLimit(@RequestBody SpotifyUnLimitRecord spotifyUnLimitRecord) throws Exception {
        spotifyUnLimitRecordMapper.update(null, Wrappers.lambdaUpdate(SpotifyUnLimitRecord.class)
                .eq(SpotifyUnLimitRecord::getId, spotifyUnLimitRecord.getId())
                .set(SpotifyUnLimitRecord::getStatus, spotifyUnLimitRecord.getStatus())
                .set(SpotifyUnLimitRecord::getUpdateTime, DateTime.now())
        );
        if (spotifyUnLimitRecord.getStatus() == SpotifyUnLimitRecord.Status.Success) {
            spotifySendMsgService.sendSpotifyUnLimitSuccessMsg(spotifyUnLimitRecord);
        }
        return GatewayResponse.SUCCESS.newBuilder().toResult();
    }
}
