package weixinrpc import ( "crypto/md5" "encoding/hex" "encoding/json" "errors" "log" "strconv" "strings" "time" "git.tetele.net/tgo/crypter" ) /** * 签名 */ func Sign(data string, salt string) string { var build strings.Builder build.WriteString(data) build.WriteString(salt) build.WriteString(DES_KEY) data_str := build.String() h := md5.New() h.Write([]byte(data_str)) // 需要加密的字符串 return hex.EncodeToString(h.Sum(nil)) // 输出加密结果 } /** * 验证签名 */ func CheckSign(sign_str, data, salt string) bool { sign := Sign(data, salt) if strings.Compare(sign_str, sign) > -1 { return true } return false } /** * 解密 */ func GetOrgData(res *Response) (string, error) { res_data := res.GetData() if res_data == "" { return "", errors.New("未收到收据") } time_int64, err := strconv.ParseInt(res.GetTime(), 10, 64) if err != nil { return "", err } now_int64 := time.Now().Unix() if now_int64-time_int64 > 10 || time_int64-now_int64 > 10 { //时间误差前后10秒,返回 return "", errors.New("返回时间错误") } check_sign := CheckSign(res.GetSign(), res_data, res.GetTime()) if !check_sign { return "", errors.New("返回数据签名错误") } //解密 res_data_de := crypter.DesDe(res_data, DES_KEY) return res_data_de, nil } /** * 处理返回结果 */ func HandleRes(res *Response) (*WxApiRes, error) { //解密 res_data_de, err := GetOrgData(res) log.Println("res_data_de", res_data_de) if err != nil { return nil, err } var res_arr WxApiRes err = json.Unmarshal([]byte(res_data_de), &res_arr) if err != nil { return nil, err } return &res_arr, nil }