package models

import (
	"bytes"
	"crypto/md5"
	"encoding/hex"
	"encoding/json"
	"errors"
	"fmt"
	"go-admin/logger"
	"io"
	"io/ioutil"
	"net/http"
	"net/url"
	"time"
)

var exchangeClient = ExchangeClient{
	Name:     "diwei",
	Password: "deovo123",
	BaseURL:  "http://api.china95059.net:8080",
}

type ExchangeClient struct {
	Name     string
	Password string
	BaseURL  string
}

type GreentownClient struct {
	UserName string
	Password string
	BaseURL  string
}

var townClient = GreentownClient{
	UserName: "diwei",
	Password: "vAoBFjuGCOEx",
	BaseURL:  "http://121.41.98.232:8001/sms",
}

const (
	GtUrlRouteSendMessage = "/api/sendMessage"
)

type GtSendMessageResp struct {
	Code     int    `json:"code"`
	Message  string `json:"message"`
	MsgId    int    `json:"msgId"`
	SmsCount int    `json:"smsCount"`
}

func GtSendMessage(phoneList []string, content string) error {
	if len(phoneList) > GetSmsNumberRemaining() { // 待发送短信超出剩余可用数量
		return errors.New("短信剩余数量不足")
	}

	params := make(map[string]interface{}, 0)
	nowTime := time.Now()
	fmt.Println("nowTime.UnixMicro", nowTime.UnixMilli())
	params["timestamp"] = nowTime.UnixMilli()
	params["phoneList"] = phoneList
	params["content"] = content
	params["sign"] = townClient.sign(content, nowTime)
	resp := &GtSendMessageResp{}
	err := townClient.post(townClient.BaseURL+GtUrlRouteSendMessage, params, resp)
	if err != nil {
		logger.Error("townClient post err:", logger.Field("err", err))
		return err
	}
	fmt.Println("resp:", resp)

	// 更新已使用的短信数量
	err = UpdateSmsUsedCount(len(phoneList))
	if err != nil {
		logger.Error("UpdateSmsUsedCount err", logger.Field("sms count", len(phoneList)), logger.Field("err", err))
		return err
	}

	return nil
}

func (g *GreentownClient) post(amApi string, params map[string]interface{}, resp interface{}) error {
	params["userName"] = g.UserName
	data, err := json.Marshal(params)
	if err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}
	req, err := http.NewRequest("POST", amApi, bytes.NewReader(data))
	if err != nil {
		logger.Error("NewRequest err:", logger.Field("err", err))
		return err
	}
	req.Header.Set("Accept", "application/json")
	req.Header.Set("Content-Type", "application/json;charset=utf-8")
	res, err := http.DefaultClient.Do(req)
	if err != nil {
		logger.Error("DefaultClient  err:", logger.Field("err", err))
		return err
	}

	readAll, err := io.ReadAll(res.Body)
	if err != nil {
		logger.Error("ReadAll  err:", logger.Field("err", err))
		return err
	}

	if err = json.Unmarshal(readAll, resp); err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}

	fmt.Println("readAll:", string(readAll))
	return nil
}

func (g *GreentownClient) sign(content string, now time.Time) string {
	return MD5Encode32(g.UserName + content + fmt.Sprintf("%d", now.UnixMilli()) + MD5Encode32(g.Password))
}

func MD5Encode32(data string) string {
	h := md5.New()
	h.Write([]byte(data))
	return hex.EncodeToString(h.Sum(nil))
}

//账号：diwei
//密码：deovo123
//func ExchangeLatestUSD() (float64, error) {
//	//params := &url.Values{}
//	//latestUSDResp := &LatestUSDResp{}
//	//err := exchangeClient.get("/latest/USD", params, latestUSDResp)
//	//if err != nil {
//	//	log.Error().Msgf("err:%#v",logger.Field("err",err))
//	//	return 0, err
//	//}
//	//return latestUSDResp.ConversionRates.CNY, nil
//}

//&mobile=15015001500 &msg=【绿城信息】您

func SmsSend(tel, content string) error {
	params := &url.Values{}
	params.Set("mobile", tel)
	params.Set("msg", content)

	//latestUSDResp := &LatestUSDResp{}
	err := exchangeClient.get("/sms/send?", params, nil)
	if err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}

	return nil
}

////https://v6.exchangerate-api.com/v6/a9208b64e4f178642020790f/latest/USD

func (m *ExchangeClient) get(amApi string, params *url.Values, resp interface{}) error {
	params.Set("name", m.Name)
	params.Set("pswd", m.Password)

	uri := m.BaseURL + amApi
	fmt.Println("uri:", uri)
	fmt.Println("uri:", uri+params.Encode())
	req, err := http.NewRequest("GET", uri+params.Encode(), nil)
	if err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}

	req.Header.Set("Content-Type", "application/json")
	res, err := (&http.Client{}).Do(req)
	if err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}
	defer res.Body.Close()

	data, err := ioutil.ReadAll(res.Body)
	if err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}
	//fmt.Println("返回数据data:")
	fmt.Println("Body:", string(data))
	//if err = json.Unmarshal(data, &resp); err != nil {
	//	logger.Error("err:",logger.Field("err",err))
	//	return err
	//}
	return nil
}

func (m *ExchangeClient) post(amApi string, params, resp interface{}) error {
	uri := m.BaseURL + amApi
	data, err := json.Marshal(params)
	if err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}

	req, err := http.NewRequest("POST", uri, bytes.NewReader(data))
	if err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}

	req.Header.Set("Content-Type", "application/json")
	res, err := (&http.Client{}).Do(req)
	if err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}
	defer res.Body.Close()

	//fmt.Println("返回数据data:")
	//fmt.Println("Body:", string(data))
	data, err = ioutil.ReadAll(res.Body)
	if err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}
	if err = json.Unmarshal(data, resp); err != nil {
		logger.Error("err:", logger.Field("err", err))
		return err
	}
	return nil
}
