wechat_params.go 2.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105
  1. package gopay
  2. import (
  3. "bytes"
  4. "crypto/hmac"
  5. "crypto/md5"
  6. "crypto/sha256"
  7. "encoding/hex"
  8. "log"
  9. "strings"
  10. )
  11. //JSAPI支付,支付参数后,再次计算出小程序用的paySign
  12. func GetMiniPaySign(appId, nonceStr, prepayId, signType, timeStamp, secretKey string) (paySign string) {
  13. buffer := new(bytes.Buffer)
  14. buffer.WriteString("appid=")
  15. buffer.WriteString(appId)
  16. buffer.WriteString("&nonceStr=")
  17. buffer.WriteString(nonceStr)
  18. buffer.WriteString("&package=")
  19. buffer.WriteString(prepayId)
  20. buffer.WriteString("&signType=")
  21. buffer.WriteString(signType)
  22. buffer.WriteString("&timeStamp=")
  23. buffer.WriteString(timeStamp)
  24. buffer.WriteString("&key=")
  25. buffer.WriteString(secretKey)
  26. signStr := buffer.String()
  27. var hashSign []byte
  28. if signType == SignType_MD5 {
  29. log.Println("signStr:", signStr)
  30. hash := md5.New()
  31. hash.Write([]byte(signStr))
  32. hashSign = hash.Sum(nil)
  33. } else {
  34. hash := hmac.New(sha256.New, []byte(secretKey))
  35. hash.Write([]byte(signStr))
  36. hashSign = hash.Sum(nil)
  37. }
  38. paySign = strings.ToUpper(hex.EncodeToString(hashSign))
  39. return
  40. }
  41. //本地通过支付参数计算Sign值
  42. func getLocalSign(secretKey string, signType string, body BodyMap) (sign string) {
  43. signStr := sortSignParams(secretKey, body)
  44. //fmt.Println("signStr:", signStr)
  45. var hashSign []byte
  46. if signType == SignType_MD5 {
  47. hash := md5.New()
  48. hash.Write([]byte(signStr))
  49. hashSign = hash.Sum(nil)
  50. } else {
  51. hash := hmac.New(sha256.New, []byte(secretKey))
  52. hash.Write([]byte(signStr))
  53. hashSign = hash.Sum(nil)
  54. }
  55. sign = strings.ToUpper(hex.EncodeToString(hashSign))
  56. return
  57. }
  58. //从微信提供的接口获取:SandboxSignKey
  59. func getSanBoxSign(mchId, nonceStr, secretKey, signType string) (key string, err error) {
  60. body := make(BodyMap)
  61. body.Set("mch_id", mchId)
  62. body.Set("nonce_str", nonceStr)
  63. //计算沙箱参数Sign
  64. sanboxSign := getLocalSign(secretKey, signType, body)
  65. //沙箱环境:获取key后,重新计算Sign
  66. key, err = getSanBoxSignKey(mchId, nonceStr, sanboxSign)
  67. if err != nil {
  68. return "", err
  69. }
  70. return
  71. }
  72. //生成请求XML的Body体
  73. func generateXml(bm BodyMap) (reqXml string) {
  74. buffer := new(bytes.Buffer)
  75. buffer.WriteString("<xml>")
  76. for k, v := range bm {
  77. buffer.WriteString("<")
  78. buffer.WriteString(k)
  79. buffer.WriteString("><![CDATA[")
  80. valueStr := convert2String(v)
  81. buffer.WriteString(valueStr)
  82. buffer.WriteString("]]></")
  83. buffer.WriteString(k)
  84. buffer.WriteString(">")
  85. }
  86. buffer.WriteString("</xml>")
  87. reqXml = buffer.String()
  88. return
  89. }