package com.ruoyi.ai.service.impl;

import com.alibaba.fastjson.JSON;
import com.fasterxml.jackson.annotation.JsonInclude;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.ruoyi.ai.domain.*;
import com.ruoyi.ai.service.*;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.domain.entity.AiUser;
import com.ruoyi.common.exception.ServiceException;
import com.ruoyi.common.utils.SecurityUtils;
import com.ruoyi.common.utils.http.OkHttpUtils;
import com.ruoyi.common.utils.sign.HmacSha256Utils;
import lombok.extern.slf4j.Slf4j;
import okhttp3.*;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.util.EntityUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Service;

import javax.servlet.http.HttpServletRequest;
import java.math.BigDecimal;
import java.text.SimpleDateFormat;
import java.util.Base64;
import java.util.Date;
import java.util.UUID;

@Service
@Slf4j
public class KaDaService implements IKaDaService {

    private final ObjectMapper objectMapper = new ObjectMapper().setSerializationInclusion(JsonInclude.Include.NON_NULL);

    @Value("${kada.url}")
    private String url;
    @Value("${kada.appId}")
    private String appId;
    @Value("${kada.secret}")
    private String secret;
    @Value("${kada.notifyUrl}")
    private String notifyUrl;
    @Value("${kada.returnUrl}")
    private String returnUrl;
    @Autowired
    private IAiUserService aiUserService;
    @Autowired
    private IAiRechargeGiftGearService aiRechargeGiftGearService;
    @Autowired
    private IAiRechargeService aiRechargeService;
    @Autowired
    private IAiRechargeGiftService aiRechargeGiftService;
    @Autowired
    private IExchangeRateService exchangeRateService;


    @Override
    public PayResVO pay(Long gearId) throws Exception {

        //充值挡位查询
        AiRechargeGiftGear aiRechargeGiftGear = aiRechargeGiftGearService.selectAiRechargeGiftGearById(gearId);
        if (aiRechargeGiftGear == null) {
            throw new ServiceException("The gear position does not exist.", -1);
        }
        BigDecimal amount = aiRechargeGiftGear.getRechargeAmount();
        // 使用汇率服务转换金额（从CNY转换为目标货币，默认PHP）
        amount = exchangeRateService.convertAmount(amount, "USD", "PHP");

        String uuid = UUID.randomUUID().toString().replaceAll("-", "").substring(0, 8);
        String dateTime = new SimpleDateFormat("yyyyMMdd").format(new Date());
        String orderNo = dateTime + "kd" + uuid;

        KaDaBodyReq req = new KaDaBodyReq();
        req.setAmount(amount);
        req.setPm("GCASH");
        req.setRef(orderNo);
        req.setPayer(new KaDaPayer());
        req.setRedirect(notifyUrl + "/recharge");
        req.setCallbackUrl(returnUrl + "/api/pay/kada-callBack");
        String json = JSON.toJSONString(req);
        String timestamp = String.valueOf(System.currentTimeMillis());
        String sign = timestamp + "." + json;
        sign = HmacSha256Utils.hmacSha256To16Hex(sign, secret);
        // 3. 构建 POST 请求
        String Basic = appId + ":" + sign;
        String encode = "Basic " + Base64.getEncoder().encodeToString(Basic.getBytes());
        CloseableHttpClient client = HttpClients.createDefault();
        HttpPost post = new HttpPost(url+"/api/mcht/payment/submit");
        post.setHeader("Content-Type", "application/json");
        post.setHeader("Authorization", encode);
        post.setHeader("Request-Time", timestamp);
        post.setEntity(new StringEntity(json, "UTF-8"));
        CloseableHttpResponse response = client.execute(post);
        int status = response.getStatusLine().getStatusCode();
        if (200 != status) {
            log.error("kada支付请求的响应异常 {}", json);
            throw new Exception("kadapay responsebody is null");
        }
        String respString = EntityUtils.toString(response.getEntity(), "UTF-8");
        KaDaBodyRes kaDaBodyRes = objectMapper.readValue(respString, KaDaBodyRes.class);
        // 创建充值管理
        AiUser userInfo = aiUserService.getUserInfo(SecurityUtils.getAiUserId());
        AiRecharge aiRecharge = new AiRecharge();
        aiRecharge.setOrderNum(orderNo);
        aiRecharge.setUserId(SecurityUtils.getAiUserId());
        aiRecharge.setAmount(amount);
        aiRecharge.setGearId(gearId);
        aiRecharge.setSource(userInfo.getSource());
        aiRecharge.setGearAmount(aiRechargeGiftGear.getRechargeAmount());
        AiRechargeGift aiRechargeGift = aiRechargeGiftService.selectAiRechargeGiftById(aiRechargeGiftGear.getRechargeId());
        aiRecharge.setPayType(aiRechargeGift.getPayType());
        aiRecharge.setPayUrl(kaDaBodyRes.getData().getPaymentUrl());
        aiRechargeService.insertAiRecharge(aiRecharge);
        PayResVO payResVO = new PayResVO();
        payResVO.setOrderNo(orderNo);
        payResVO.setPayUrl(kaDaBodyRes.getData().getPaymentUrl());
        return payResVO;
    }

    @Override
    public AjaxResult callBack(HttpServletRequest request, KaDaBodyCall req) throws Exception {
        String status = req.getStatus();
        String ref = req.getRef();
        if (!"COMPLETE".equals(status)){
            log.error("kada支付失败 {}", ref);
            return null;
        }
        String timestamp = request.getHeader("Request-Time");
        String signature = request.getHeader("Signature");
        String Authorization = request.getHeader("Authorization");
        String json = JSON.toJSONString(req);
        String sign = timestamp + "." + json;
        sign = HmacSha256Utils.hmacSha256To16Hex(sign, secret);
        String Basic = appId + ":" + sign;
        String encode = "Basic " + Base64.getEncoder().encodeToString(Basic.getBytes());
        if (!signature.equals(sign)) {
            log.error("kada支付回调签名错误 {}", ref);
            log.error("kada支付回调时间 {}", timestamp);
            log.error("kada支付回调签名 {}", signature);
            log.error("kada支付回调认证头 {}", Authorization);
            log.error("kada支付回调报文 {}", json);
            log.error("我方kada支付回调验证签名 {}", sign);
            log.error("我方kada支付回调验证认证头 {}", encode);
            return AjaxResult.error();
        }
        //充值成功处理
        aiRechargeService.addRecharge(ref);
        return AjaxResult.success();
    }


}
