using BasePaySdk;
using BasePaySdk.Request;
using JiaZhiQuan.Common.Config;
using JiaZhiQuan.Common.Utils;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using Wicture.DbRESTFul;

namespace JiaZhiQuan.Common.JuheAPI.HuiFu {
    public static class HuiFuUtil {

        public static bool CheckSign(string huifuPubKey,string sign,
            object data,bool isAsync=false) {
            string dataStr = null;
            if (isAsync) {
                dataStr= JsonConvert.SerializeObject(data);
            } else {
                var str = JsonConvert.SerializeObject(data);
                dataStr = sort4JsonString(str);
            }
            return RsaUtils.verfySign(huifuPubKey, sign,dataStr);
        }
        public static string sort4JsonString(string sourceJson) {

            var dic = JsonConvert.DeserializeObject<SortedDictionary<string, object>>(sourceJson);
            SortedDictionary<string, object> keyValues = new SortedDictionary<string, object>(dic);
            var result = keyValues.OrderBy(m => m.Key);//升序 把Key换成Value 就是对Value进行排序
            //var result = keyValues.OrderByDescending(m => m.Key);//降序
            Dictionary<string, object> resultDic = result.ToDictionary(x => x.Key, x => x.Value);
            return JsonConvert.SerializeObject(resultDic);
        }

        public static void InitConfig(HuiFuCommonConfig huifuConf) {
            MerConfig config = new MerConfig {
                ProductId = huifuConf.product_id,
                SysId = huifuConf.sys_id,
                RsaPrivateKey = huifuConf.app_secret_key,
                RsaPublicKey = huifuConf.huifu_pub_key
            };
            //BasePay.debug = isDev;
            BasePay.debug = true;
            //BasePay.prodMode = !BasePay.debug;
            BasePay.prodMode = true;
            BasePay.initWithMerConfig(config);
        }

        public static void InitNoticeUrl(this HuiFuReqBase reqInfo, ConfigFromDb config) {
            reqInfo.notifyUrl = reqInfo.ReqType() switch {
                HuiFuReqTypeEnums.Jspay => config.HuiFuJspayCallbackUrl,
                HuiFuReqTypeEnums.Chash => config.HuiFuChashCallbackUrl,
                HuiFuReqTypeEnums.Open => config.HuiFuOpenCallbackUrl,
                HuiFuReqTypeEnums.Refund => config.HuiFuRefundCallbackUrl,
                HuiFuReqTypeEnums.OpenModify => config.HuiFuOpenCallbackUrl,
               HuiFuReqTypeEnums.YuEPay => config.HuiFuYuEPayCallbackUrl,
                _ => ""
            };
        }

        /// <summary>
        /// 流水号前缀
        /// </summary>
        /// <param name="reqType"></param>
        /// <returns></returns>
        public static void InitReqId(HuiFuReqBase info) {
            var pre = info.ReqType() switch {
                HuiFuReqTypeEnums.Jspay => "P",
                HuiFuReqTypeEnums.Chash => "C",
                HuiFuReqTypeEnums.Open => "O",
                HuiFuReqTypeEnums.Refund => "R",
                HuiFuReqTypeEnums.Indv => "I",
                HuiFuReqTypeEnums.RefundQuery => "RQ",
                HuiFuReqTypeEnums.OpenModify =>"OM",
                HuiFuReqTypeEnums.YuEPay => "Y",
                _ => ""
            };

            info.reqId = (info.orgId.Length+6)>32? info.orgId: pre + info.orgId + "A" + StrEncryUtils.GetRandom(4);
        }

        public static TResp Request<TResp>(HuiFuCommonConfig huifuConf,
            HuiFuReqBase info) {
            InitConfig(huifuConf);
            BaseRequest request;
            string reqTypeStr = "";
            if (info is HuiFuPayInfo pInfo) {
                request = HuiFuApiJspay.InitReq(huifuConf, pInfo);
                reqTypeStr=pInfo.ReqType().ToString();
            } else if(info is HuiFuRefundInfo rInfo) {
                request = HuiFuApiRefund.InitReq(huifuConf, rInfo);
                reqTypeStr = rInfo.ReqType().ToString();
            } else if (info is HuiFuOpenInfo oInfo) {
                request = HuiFuApiOpen.InitReq(huifuConf, oInfo);
                reqTypeStr = oInfo.ReqType().ToString();
            } else if (info is HuiFuChashInfo cInfo) {
                request = HuiFuApiChash.InitReq(huifuConf, cInfo);
                reqTypeStr = cInfo.ReqType().ToString();
            } else if (info is HuiFuIndvInfo iInfo) {
                request = HuiFuApiIndv.InitReq(huifuConf, iInfo);
                reqTypeStr = iInfo.ReqType().ToString();
            } else if (info is HuiFuRefundQueryInfo rqInfo) {
                request = HuiFuApiRefundQuery.InitReq(huifuConf, rqInfo);
                reqTypeStr = rqInfo.ReqType().ToString();
            } else if (info is HuiFuOpenModifyInfo omInfo) {
                request = HuiFuApiOpenModify.InitReq(huifuConf, omInfo);
                reqTypeStr = omInfo.ReqType().ToString();
            } else if (info is HuiFuYuEPayInfo yInfo) {
                request = HuiFuApiYuEPay.InitReq(huifuConf, yInfo);
                reqTypeStr = yInfo.ReqType().ToString();
            } else {
                throw new Exception("不支持的汇付接口");
            }
            try {
                Dictionary<string, Object> result = null;
                LoggerManager.Logger.Info($"{reqTypeStr} 请求入参：" + JsonConvert.SerializeObject(request));
                result = BasePayClient.postRequest(request, null);
                LoggerManager.Logger.Info($"{reqTypeStr} 响应结果：" + JsonConvert.SerializeObject(result));
                var rstStr = JsonConvert.SerializeObject(result);
                var rst = JsonConvert.DeserializeObject<TResp>(rstStr);
                return rst;
            } catch (Exception ex) {
                LoggerManager.Logger.Error($"{reqTypeStr} 请求异常" + ex.Message);
                return default;
            }
        }
    }
}
