From fffd5d34c7cfb79d8284fecb26507878ba1a3026 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E8=8B=8F=E5=B0=B9=E5=B2=9A?= <770236076@qq.com> Date: Thu, 24 Dec 2020 16:19:53 +0800 Subject: [PATCH] a --- platformapi/txcloudapi/txcloudapi.go | 141 ++++++++++++++++++++++ platformapi/txcloudapi/txcloudapi_test.go | 29 +++++ 2 files changed, 170 insertions(+) create mode 100644 platformapi/txcloudapi/txcloudapi.go create mode 100644 platformapi/txcloudapi/txcloudapi_test.go diff --git a/platformapi/txcloudapi/txcloudapi.go b/platformapi/txcloudapi/txcloudapi.go new file mode 100644 index 00000000..75ee52f4 --- /dev/null +++ b/platformapi/txcloudapi/txcloudapi.go @@ -0,0 +1,141 @@ +package txcloudapi + +import ( + "crypto/hmac" + "crypto/sha1" + "encoding/base64" + "fmt" + "net/http" + "time" + + "git.rosy.net.cn/baseapi" + "git.rosy.net.cn/baseapi/platformapi" + "git.rosy.net.cn/baseapi/utils" +) + +const ( + source = "market" + + StatusErr = -1 //单号或代码错误 + StatusNull = 0 //暂无轨迹 + StatusAccept = 1 //快递收件 + StatusDelivering = 2 //在途中 + StatusFinished = 3 //已签收 + StatusProblem = 4 //问题件 (派件不成功或要求择日派送) + StatusException = 5 //疑难件(收件人拒绝签收,地址有误或不能送达派送区域,收费等原因无法正常派送) + StatusFailed = 6 //退件签收 +) + +type API struct { + secretID string + secretKey string + client *http.Client + config *platformapi.APIConfig +} + +func New(secretID, secretKey string, config ...*platformapi.APIConfig) *API { + curConfig := platformapi.DefAPIConfig + if len(config) > 0 { + curConfig = *config[0] + } + return &API{ + secretID: secretID, + secretKey: secretKey, + client: &http.Client{Timeout: curConfig.ClientTimeout}, + config: &curConfig, + } +} + +func calcAuthorization(source string, secretId string, secretKey string) (auth string, datetime string, err error) { + timeLocation, _ := time.LoadLocation("Etc/GMT") + datetime = time.Now().In(timeLocation).Format("Mon, 02 Jan 2006 15:04:05 GMT") + signStr := fmt.Sprintf("x-date: %s\nx-source: %s", datetime, source) + + // hmac-sha1 + mac := hmac.New(sha1.New, []byte(secretKey)) + mac.Write([]byte(signStr)) + sign := base64.StdEncoding.EncodeToString(mac.Sum(nil)) + + auth = fmt.Sprintf("hmac id=\"%s\", algorithm=\"hmac-sha1\", headers=\"x-date x-source\", signature=\"%s\"", + secretId, sign) + + return auth, datetime, nil +} + +func (a *API) AccessAPI(url string, params map[string]interface{}) (retVal map[string]interface{}, err error) { + // 签名 + auth, datetime, _ := calcAuthorization(source, a.secretID, a.secretKey) + err = platformapi.AccessPlatformAPIWithRetry(a.client, + func() *http.Request { + request, _ := http.NewRequest(http.MethodGet, utils.GenerateGetURL(url, "", params), nil) + request.Header.Set("X-Source", source) + request.Header.Set("X-Date", datetime) + request.Header.Set("Authorization", auth) + request.Header.Set("Content-Type", "application/x-www-form-urlencoded") + return request + }, + a.config, + func(response *http.Response, bodyStr string, jsonResult1 map[string]interface{}) (errLevel string, err error) { + if jsonResult1 == nil { + return platformapi.ErrLevelRecoverableErr, fmt.Errorf("mapData is nil") + } + if err == nil { + if jsonResult1["code"].(string) != "OK" { + errLevel = platformapi.ErrLevelGeneralFail + err = utils.NewErrorCode(jsonResult1["msg"].(string), jsonResult1["code"].(string)) + baseapi.SugarLogger.Debugf("txcloud AccessAPI failed, jsonResult1:%s", utils.Format4Output(jsonResult1, true)) + } + retVal = jsonResult1 + } + return errLevel, err + }) + return retVal, err +} + +type GetWaybillDetailInfoResult struct { + Code string `json:"code"` + No string `json:"no"` + Type string `json:"type"` + List []struct { + Content string `json:"content"` + Time string `json:"time"` + } `json:"list"` + State string `json:"state"` + Msg string `json:"msg"` + Name string `json:"name"` + Site string `json:"site"` + Phone string `json:"phone"` + Logo string `json:"logo"` + Courier string `json:"courier"` + CourierPhone string `json:"courierPhone"` + UpdateTime string `json:"updateTime"` + TakeTime string `json:"takeTime"` +} + +func (a *API) GetWaybillDetailInfo(vendorWaybillID, comType string) (getWaybillDetailInfoResult *GetWaybillDetailInfoResult, err error) { + params := map[string]interface{}{ + "num": vendorWaybillID, + } + if comType != "" { + params["com"] = comType + } + result, err := a.AccessAPI("https://service-5hof02so-1300683954.gz.apigw.tencentcs.com/release/kuaidi", params) + if err == nil { + utils.Map2StructByJson(result, &getWaybillDetailInfoResult, false) + } + return getWaybillDetailInfoResult, err +} + +func (a *API) Address(vendorWaybillID, comType string) (getWaybillDetailInfoResult *GetWaybillDetailInfoResult, err error) { + params := map[string]interface{}{ + "num": vendorWaybillID, + } + if comType != "" { + params["com"] = comType + } + result, err := a.AccessAPI("https://service-5hof02so-1300683954.gz.apigw.tencentcs.com/release/kuaidi", params) + if err == nil { + utils.Map2StructByJson(result, &getWaybillDetailInfoResult, false) + } + return getWaybillDetailInfoResult, err +} diff --git a/platformapi/txcloudapi/txcloudapi_test.go b/platformapi/txcloudapi/txcloudapi_test.go new file mode 100644 index 00000000..668fc49f --- /dev/null +++ b/platformapi/txcloudapi/txcloudapi_test.go @@ -0,0 +1,29 @@ +package txcloudapi + +import ( + "testing" + + "git.rosy.net.cn/baseapi" + "git.rosy.net.cn/baseapi/utils" + "go.uber.org/zap" +) + +var ( + api *API + sugarLogger *zap.SugaredLogger +) + +func init() { + logger, _ := zap.NewDevelopment() + sugarLogger = logger.Sugar() + baseapi.Init(sugarLogger) + api = New("AKIDFNmm1U7vhITlVItry0ng5Q268lGjDZyQUR6", "25p3aynr97hOMJEfpvr0LoXD0gI62l7wcHA7nsM6") +} + +func TestGetWaybillDetailInfo(t *testing.T) { + result, err := api.GetWaybillDetailInfo("JDVD01294351024", "") + if err != nil { + t.Fatal(err) + } + t.Log(utils.Format4Output(result, false)) +}