蛋蛋星球-客户端
選択できるのは25トピックまでです。 トピックは、先頭が英数字で、英数字とダッシュ('-')を使用した35文字以内のものにしてください。

check.go 2.8 KiB

1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
3週間前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
1ヶ月前
2週間前
2週間前
2週間前
2週間前
2週間前
2週間前
2週間前
2週間前
2週間前
2週間前
2週間前
1ヶ月前
1ヶ月前
2週間前
123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108
  1. package aes
  2. import (
  3. "applet/app/lib/aes/md"
  4. "applet/app/utils"
  5. "bytes"
  6. "encoding/json"
  7. "errors"
  8. "fmt"
  9. "github.com/gin-gonic/gin"
  10. "io/ioutil"
  11. "strconv"
  12. "strings"
  13. "time"
  14. )
  15. func CheckSign(c *gin.Context) error {
  16. var query = map[string]string{}
  17. //1、从请求头中获取必传参数
  18. query["timestamp"] = c.GetHeader("timestamp")
  19. query["nonce"] = c.GetHeader("nonce")
  20. if len(query["nonce"]) != 32 {
  21. return errors.New("随机字符串有误!")
  22. }
  23. sign := c.GetHeader("sign")
  24. //2、判断请求方式,以获取请求参数
  25. if c.Request.Method == "GET" {
  26. queryParams := c.Request.URL.Query()
  27. for key, values := range queryParams {
  28. if len(values) > 0 {
  29. query[key] = values[0]
  30. }
  31. }
  32. } else {
  33. body, _ := ioutil.ReadAll(c.Request.Body)
  34. if string(body) != "" {
  35. fmt.Println("body:" + string(body))
  36. str, err := AesDecryptByECB(md.AesKey, string(body))
  37. if err != nil {
  38. return err
  39. }
  40. if str != "" {
  41. c.Request.Body = ioutil.NopCloser(bytes.NewBuffer([]byte(str)))
  42. var bodyParams = map[string]interface{}{}
  43. err = json.Unmarshal([]byte(str), &bodyParams)
  44. if err != nil {
  45. return err
  46. }
  47. for key, value := range bodyParams {
  48. // 使用类型断言判断是否为 string 类型
  49. if _, ok := value.(map[string]interface{}); ok {
  50. query[key] = utils.SerializeStr(value)
  51. } else {
  52. query[key] = utils.AnyToString(value)
  53. }
  54. }
  55. }
  56. }
  57. }
  58. //3.query参数按照 ASCII 码从小到大排序
  59. str := utils.JoinStringsInASCII(query, "&", false, false, "")
  60. //4.md5加密 转小写
  61. signValue := strings.ToLower(utils.Md5(str))
  62. //5.判断跟前端传来的sign是否一致
  63. if sign != signValue {
  64. return errors.New("非法签名!")
  65. }
  66. //6、判断时效性
  67. currentTimestamp := time.Now().Unix()
  68. storedTimestamp, err := strconv.ParseInt(query["timestamp"], 10, 64)
  69. if err != nil {
  70. return err
  71. }
  72. if isMillisecond(storedTimestamp) {
  73. //TODO::兼容客户端传毫秒
  74. currentTimestamp = time.Now().UnixMilli()
  75. if currentTimestamp-storedTimestamp > 60*5*1000 { // 2分钟
  76. fmt.Println("currentTimestamp>>>>>:", currentTimestamp)
  77. fmt.Println("storedTimestamp>>>>>:", storedTimestamp)
  78. return fmt.Errorf("签名过期~")
  79. }
  80. if currentTimestamp-storedTimestamp < -60*1000 { //避免客户端传过快时间的误差
  81. return errors.New("签名超前~")
  82. }
  83. } else {
  84. if currentTimestamp-storedTimestamp > 60*5 { // 2分钟
  85. fmt.Println("currentTimestamp>>>>>:", currentTimestamp)
  86. fmt.Println("storedTimestamp>>>>>:", storedTimestamp)
  87. return fmt.Errorf("签名过期!")
  88. }
  89. if currentTimestamp-storedTimestamp < -60 { //避免客户端传过快时间的误差
  90. return errors.New("签名超前!")
  91. }
  92. }
  93. return nil
  94. }
  95. func isMillisecond(timestamp int64) bool {
  96. return timestamp > 1e12 && timestamp < 1e13
  97. }