|
@@ -0,0 +1,91 @@ |
|
|
|
|
|
package zhios_pay_utils |
|
|
|
|
|
|
|
|
|
|
|
import ( |
|
|
|
|
|
"crypto" |
|
|
|
|
|
"crypto/rand" |
|
|
|
|
|
"crypto/rsa" |
|
|
|
|
|
"encoding/base64" |
|
|
|
|
|
"fmt" |
|
|
|
|
|
"golang.org/x/crypto/ssh" |
|
|
|
|
|
"sort" |
|
|
|
|
|
"strings" |
|
|
|
|
|
) |
|
|
|
|
|
|
|
|
|
|
|
func GetSign(method, privateKeyStr string, param map[string]interface{}) (string, error) { |
|
|
|
|
|
privateKey, err := ssh.ParseRawPrivateKey([]byte(privateKeyStr)) |
|
|
|
|
|
if err != nil { |
|
|
|
|
|
return "", err |
|
|
|
|
|
} |
|
|
|
|
|
keys := make([]string, 0, len(param)) |
|
|
|
|
|
for k := range param { |
|
|
|
|
|
keys = append(keys, k) |
|
|
|
|
|
} |
|
|
|
|
|
sort.Strings(keys) |
|
|
|
|
|
data := "/api" + method |
|
|
|
|
|
for _, v := range keys { |
|
|
|
|
|
if strings.Contains(data, "?") == false { |
|
|
|
|
|
data += "?" + v + "=" + param[v].(string) |
|
|
|
|
|
} else { |
|
|
|
|
|
data += "&" + v + "=" + param[v].(string) |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
fmt.Println(privateKey.(*rsa.PrivateKey)) |
|
|
|
|
|
fmt.Println(data) |
|
|
|
|
|
h := crypto.Hash.New(crypto.SHA256) |
|
|
|
|
|
h.Write([]byte(data)) |
|
|
|
|
|
hashed := h.Sum(nil) |
|
|
|
|
|
sign, err := rsa.SignPKCS1v15(rand.Reader, privateKey.(*rsa.PrivateKey), crypto.SHA256, hashed) |
|
|
|
|
|
if err != nil { |
|
|
|
|
|
return "", nil |
|
|
|
|
|
} |
|
|
|
|
|
return base64.StdEncoding.EncodeToString(sign), nil |
|
|
|
|
|
} |
|
|
|
|
|
|
|
|
|
|
|
//规则: |
|
|
|
|
|
//◆ 参数名ASCII码从小到大排序(字典序); |
|
|
|
|
|
//◆ 如果参数的值为空不参与签名; |
|
|
|
|
|
//◆ 参数名区分大小写; |
|
|
|
|
|
//◆ 接口請求成功時,需對返回參數使用平台提供的公鑰進行驗簽,传送的sign参数不参与签名,将生成的签名与该sign值作校验。 |
|
|
|
|
|
// |
|
|
|
|
|
// JoinStringsInASCII |
|
|
|
|
|
// @Description: 按照规则,参数名ASCII码从小到大排序后拼接 |
|
|
|
|
|
// @param data 待拼接的数据 |
|
|
|
|
|
// @param sep 连接符 |
|
|
|
|
|
// @param onlyValues 是否只包含参数值,true则不包含参数名,否则参数名和参数值均有 |
|
|
|
|
|
// @param includeEmpty 是否包含空值,true则包含空值,否则不包含,注意此参数不影响参数名的存在 |
|
|
|
|
|
// @param exceptKeys 被排除的参数名,不参与排序及拼接 |
|
|
|
|
|
// @return string |
|
|
|
|
|
// |
|
|
|
|
|
func JoinStringsInASCII(data map[string]string, sep, KeyValueSep string, onlyValues, includeEmpty bool, exceptKeys ...string) string { |
|
|
|
|
|
var list []string |
|
|
|
|
|
var keyList []string |
|
|
|
|
|
m := make(map[string]int) |
|
|
|
|
|
if len(exceptKeys) > 0 { |
|
|
|
|
|
for _, except := range exceptKeys { |
|
|
|
|
|
m[except] = 1 |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
for k := range data { |
|
|
|
|
|
if _, ok := m[k]; ok { |
|
|
|
|
|
continue |
|
|
|
|
|
} |
|
|
|
|
|
value := data[k] |
|
|
|
|
|
if !includeEmpty && value == "" { |
|
|
|
|
|
continue |
|
|
|
|
|
} |
|
|
|
|
|
if onlyValues { |
|
|
|
|
|
keyList = append(keyList, k) |
|
|
|
|
|
} else { |
|
|
|
|
|
list = append(list, fmt.Sprintf("%s%s%s", k, KeyValueSep, value)) |
|
|
|
|
|
} |
|
|
|
|
|
} |
|
|
|
|
|
if onlyValues { |
|
|
|
|
|
sort.Strings(keyList) |
|
|
|
|
|
for _, v := range keyList { |
|
|
|
|
|
list = append(list, data[v]) |
|
|
|
|
|
} |
|
|
|
|
|
} else { |
|
|
|
|
|
sort.Strings(list) |
|
|
|
|
|
} |
|
|
|
|
|
return strings.Join(list, sep) |
|
|
|
|
|
} |