wechat.go 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173
  1. package wechat
  2. import (
  3. "encoding/json"
  4. "eta/eta_mini_api/models"
  5. "eta/eta_mini_api/services/alarm_msg"
  6. "eta/eta_mini_api/utils"
  7. "fmt"
  8. "io"
  9. "net/http"
  10. "time"
  11. "github.com/silenceper/wechat/v2"
  12. "github.com/silenceper/wechat/v2/cache"
  13. "github.com/silenceper/wechat/v2/credential"
  14. "github.com/silenceper/wechat/v2/officialaccount"
  15. "github.com/silenceper/wechat/v2/officialaccount/config"
  16. "github.com/silenceper/wechat/v2/officialaccount/js"
  17. "github.com/silenceper/wechat/v2/officialaccount/user"
  18. )
  19. var (
  20. WxAppId string
  21. WxAppSecret string
  22. )
  23. type WechatAccessToken struct {
  24. }
  25. func GetWxChat() (officialAccount *officialaccount.OfficialAccount) {
  26. wc := wechat.NewWechat()
  27. memory := cache.NewMemory()
  28. conf := &config.Config{
  29. AppID: utils.DW_WX_APPID,
  30. AppSecret: utils.DW_WX_APP_SECRET,
  31. Token: "",
  32. EncodingAESKey: "",
  33. Cache: memory,
  34. }
  35. officialAccount = wc.GetOfficialAccount(conf)
  36. wechatAccessToken := &WechatAccessToken{}
  37. officialAccount.SetAccessTokenHandle(wechatAccessToken)
  38. return
  39. }
  40. var DefaultKey = "zcmRedis"
  41. // GetAccessToken 获取accessToken
  42. func (wechat WechatAccessToken) GetAccessToken() (accessToken string, err error) {
  43. wxToken, err := models.GetWxTokenById()
  44. if err != nil && err.Error() != utils.ErrNoRow() {
  45. return
  46. }
  47. //如果300s就要过期了,那么就去刷新accessToken
  48. if wxToken.ExpiresIn < time.Now().Unix()+300 {
  49. tmpAccessToken, expires, tmpErr := getTokenFromServer(utils.DW_WX_APPID, utils.DW_WX_APP_SECRET)
  50. if tmpErr != nil {
  51. err = tmpErr
  52. return
  53. }
  54. var updateCols = []string{"access_token", "expires_in"}
  55. wxToken.AccessToken = tmpAccessToken
  56. wxToken.ExpiresIn = time.Now().Unix() + expires - 600 //快过期前10分钟就刷新掉
  57. wxToken.Update(updateCols)
  58. }
  59. accessToken = wxToken.AccessToken
  60. return
  61. }
  62. // accessToken, err = utils.Redis.Get(context.TODO(), utils.CACHE_WX_ACCESS_TOKEN_DW).Result()
  63. // // wxToken, err := models.GetWxTokenById()
  64. // if err != nil && err != redis.Nil {
  65. // return
  66. // }
  67. // models.GetWxTokenById()
  68. // minConf, _ := models.GetMiniConf()
  69. // // 缓存中没有取到数据,那么就需要强制刷新的accessToken
  70. // tmpAccessToken, expires, tmpErr := getTokenFromServer(minConf["WxAppId"], minConf["WxAppSecret"])
  71. //
  72. // if tmpAccessToken == "" {
  73. // err = errors.New("获取微信token失败,Err:" + tmpErr.Error())
  74. // return
  75. // }
  76. //
  77. // redisTimeExpire := time.Duration(expires-600) * time.Second
  78. // err = utils.Redis.SetEX(context.TODO(), utils.CACHE_WX_ACCESS_TOKEN_DW, tmpAccessToken, redisTimeExpire).Err()
  79. //
  80. // if err != nil {
  81. // return
  82. // }
  83. //
  84. // err = utils.Redis.HSet(context.TODO(), DefaultKey, utils.CACHE_WX_ACCESS_TOKEN_DW, true).Err()
  85. // // err = utils.Redis.Put(utils.CACHE_WX_ACCESS_TOKEN_HZ, tmpAccessToken, redisTimeExpire)
  86. //
  87. // if err != nil {
  88. // err = errors.New("更新微信token失败")
  89. // return
  90. // }
  91. //
  92. // return
  93. // getTokenFromServer 服务端获取accessToken
  94. func getTokenFromServer(appid, wxSecret string) (accessToken string, expires int64, err error) {
  95. apiUrl := "https://api.weixin.qq.com/cgi-bin/token?grant_type=client_credential&appid=%s&secret=%s"
  96. resAccessToken, err := credential.GetTokenFromServer(fmt.Sprintf(apiUrl, appid, wxSecret))
  97. if err != nil {
  98. return
  99. }
  100. expires = resAccessToken.ExpiresIn
  101. accessToken = resAccessToken.AccessToken
  102. return
  103. }
  104. // GetUserInfo 获取微信用户详情
  105. func GetUserInfo(openid string) (userInfo *user.Info, err error) {
  106. wechatClient := GetWxChat()
  107. userClient := wechatClient.GetUser()
  108. userInfo, err = userClient.GetUserInfo(openid)
  109. return
  110. }
  111. // GetSession 获取用户详情
  112. // func GetSession(code string) (userInfo auth.ResCode2Session, err error) {
  113. // wechatClient := GetWxChat()
  114. // userClient := wechatClient.GetUser()
  115. // userInfo, err = authClient.Code2Session(code)
  116. // return
  117. // }
  118. // GetJsConfig 获取公众号jsConfig
  119. func GetJsConfig(signUrl string) (jsConf *js.Config, err error) {
  120. wechatClient := GetWxChat()
  121. j := wechatClient.GetJs()
  122. jsConf, err = j.GetConfig(signUrl)
  123. return
  124. }
  125. type WxUserInfo struct {
  126. OpenId string `json:"openid"`
  127. AccessToken string `json:"access_token"`
  128. RefreshToken string `json:"refresh_token"`
  129. Scope string `json:"scope"`
  130. ErrCode int
  131. ErrMsg string
  132. }
  133. func GetWxUserInfo(code string) (info *WxUserInfo, err error) {
  134. httpUrl := `https://api.weixin.qq.com/sns/oauth2/access_token?appid=%s&secret=%s&code=%s&grant_type=authorization_code`
  135. httpUrl = fmt.Sprintf(httpUrl, utils.DW_WX_APPID, utils.DW_WX_APP_SECRET, code)
  136. client := http.Client{}
  137. wxReq, err := http.NewRequest("GET", httpUrl, nil)
  138. if err != nil {
  139. return
  140. }
  141. response, err := client.Do(wxReq)
  142. if err != nil {
  143. return
  144. }
  145. defer response.Body.Close()
  146. body, err := io.ReadAll(response.Body)
  147. if err != nil {
  148. return
  149. }
  150. alarm_msg.SendAlarmMsg(string(body), 1)
  151. if err = json.Unmarshal(body, &info); err != nil {
  152. return
  153. }
  154. return
  155. }