Skip to content

Commit

Permalink
Merge pull request #3 from go-pay/feature/add_open_sdk
Browse files Browse the repository at this point in the history
v1.1.0
  • Loading branch information
iGoogle-ink authored Jun 8, 2022
2 parents c32bd3e + 9ab20ed commit 5603048
Show file tree
Hide file tree
Showing 24 changed files with 340 additions and 118 deletions.
40 changes: 35 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -64,26 +64,30 @@ if err != nil {
//wxsdk.DebugSwitch = wechat.DebugOn
```

- ### AccessToken 说明
- ### AccessToken 说明:微信小程序和公众号 与 开放平台的 AccessToken 不用通用。

- #### 微信小程序 or 公众号的 AccessToken
```go
// NewSDK 后,首次获取AccessToken请通过此方法获取,之后请通过下面的回调方法获取
at := wxsdk.GetAccessToken()
// New完SDK,首次获取AccessToken请通过此方法获取,之后请通过下面的回调方法获取
at := wxsdk.GetMiniOrPublicAT()
xlog.Infof("at: %s", at)

// 每次刷新 accessToken 后,此方法回调返回 accessToken 和 有效时间(秒)
wxsdk.SetAccessTokenCallback(func(accessToken string, expireIn int, err error) {
wxsdk.SetMiniOrPublicATCallback(func(accessToken string, expireIn int, err error) {
if err != nil {
xlog.Errorf("refresh access token error(%+v)", err)
return
}
xlog.Infof("accessToken: %s", accessToken)
xlog.Infof("expireIn: %d", expireIn)
})

// 若 NewSDK() 时自传 AccessToken,则后续更新替换请调用此方法
wxsdk.SetAccessToken()
wxsdk.SetMiniOrPublicAT()
```

- #### 开放平台 的AccessToken详见下方 NewOpenSDK

- ### NewMiniSDK

```go
Expand All @@ -98,6 +102,32 @@ miniSDK := wxsdk.NewMini()
publicSDK := wxsdk.NewPublic()
```

- ### NewOpenSDK

```go
// New 微信开放平台 SDK
openSDK, err = wxsdk.NewOpen()
if err != nil {
xlog.Error(err)
return
}
// 注意:必须换取 开放平台 自己的AccessToken,与小程序和公众号不通用
openAT, err := openSDK.Code2AccessToken(ctx, "xxx")
if err != nil {
xlog.Error(err)
return
}
xlog.Infof("open at: %+v", openAT)
// 每次刷新 accessToken 后,此方法回调返回 accessToken 和 有效时间(秒)
openSDK.SetOpenATCallback(func(at *open.AccessToken, err error) {
if err != nil {
xlog.Errorf("refresh access token error(%+v)", err)
return
}
xlog.Infof("AccessToken: %+v", at)
})
```

- ### 点击分别查看小程序、公众号使用文档

* #### [微信小程序](https://github.com/go-pay/wechat-sdk/blob/main/doc/mini.md)
Expand Down
10 changes: 9 additions & 1 deletion access_token.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package wechat

import (
"fmt"
"runtime"
"time"

"github.com/go-pay/wechat-sdk/mini"
Expand Down Expand Up @@ -44,7 +45,14 @@ func (s *SDK) getAccessToken() (err error) {
return nil
}

func (s *SDK) autoRefreshAccessToken() {
func (s *SDK) goAutoRefreshAccessToken() {
defer func() {
if r := recover(); r != nil {
buf := make([]byte, 64<<10)
buf = buf[:runtime.Stack(buf, false)]
xlog.Errorf("mini_public_goAutoRefreshAccessToken: panic recovered: %s\n%s", r, buf)
}
}()
for {
// every one hour, request new access token, default 10s
time.Sleep(s.RefreshInternal / 2)
Expand Down
2 changes: 1 addition & 1 deletion common.go
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ const (
DebugOff = 0
DebugOn = 1

Version = "1.0.0"
Version = "1.1.0"
)

const (
Expand Down
2 changes: 1 addition & 1 deletion doc/mini.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@

---

### 具体使用请参考 `doc/mini.md`
### 具体使用请参考 `sdk_mini_test.go`

#### Code2Session

Expand Down
34 changes: 29 additions & 5 deletions doc/open.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,20 +6,44 @@

---

### 具体使用请参考 `doc/open.md`
### 具体使用请参考 `sdk_open_test.go`

#### 通过 code 获取 access_token

```go
// 注意:必须换取 开放平台 自己的AccessToken,与小程序和公众号不通用
openAT, err := openSDK.Code2AccessToken(ctx, "xxx")
if err != nil {
xlog.Error(err)
return
}
xlog.Infof("open at: %+v", openAT)
// 每次刷新 accessToken 后,此方法回调返回 accessToken 和 有效时间(秒)
openSDK.SetOpenATCallback(func(at *open.AccessToken, err error) {
if err != nil {
xlog.Errorf("refresh access token error(%+v)", err)
return
}
xlog.Infof("AccessToken: %+v", at)
})
```

#### 通过 code 获取 access_token

```go
rsp, err := openSDK.UserInfo(ctx, "openid", "zh_CN")
if err != nil {
xlog.Error(err)
return
}
xlog.Infof("rsp:%+v", rsp)
```

## 附录:

### 微信开发平台 服务端API

* <font color='#07C160' size='4'>微信登录功能</font>
* 通过 code 获取 access_token:``sdk.()`
* 刷新或续期 access_token 使用:`sdk.()`
* 检验授权凭证 access_token 是否有效:`sdk.()`
* 获取用户个人信息(UnionID 机制):`sdk.UserTagDelete()`
* 通过 code 获取 access_token:``sdk.Code2AccessToken()`
* 检验授权凭证 access_token 是否有效:`sdk.CheckAccessToken()`
* 获取用户个人信息(UnionID 机制):`sdk.UserInfo()`
2 changes: 1 addition & 1 deletion doc/public.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@

---

### 具体使用请参考 `doc/open.md`
### 具体使用请参考 `sdk_public_test.go`

#### 创建二维码

Expand Down
28 changes: 19 additions & 9 deletions mini/customer_service.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package mini

import (
"context"
"fmt"

"github.com/go-pay/wechat-sdk/pkg/bmap"
"github.com/go-pay/wechat-sdk/pkg/util"
Expand All @@ -25,7 +26,7 @@ func (s *SDK) CSMessageGetTempMedia(c context.Context, mediaId string) (media []
// msgType:消息类型,枚举值:mini.MsgTypeText、mini.MsgTypeImage、mini.MsgTypeLink、mini.MsgTypeMiniPage
// msgValue:对应 msgType 的value值,BodyMap key-value 格式传入
// 文档:https://developers.weixin.qq.com/miniprogram/dev/api-backend/open-api/customer-message/customerServiceMessage.send.html
func (s *SDK) CSMessageSend(c context.Context, toUser string, msgType MsgType, msgValue bmap.BodyMap) (ec *ErrorCode, err error) {
func (s *SDK) CSMessageSend(c context.Context, toUser string, msgType MsgType, msgValue bmap.BodyMap) (err error) {
path := "/cgi-bin/message/custom/send?access_token=" + s.Conf.AccessToken
body := make(bmap.BodyMap)
body.Set("touser", toUser)
Expand All @@ -43,19 +44,22 @@ func (s *SDK) CSMessageSend(c context.Context, toUser string, msgType MsgType, m
body.Set("msgtype", "miniprogrampage").
Set("text", msgValue)
}
ec = &ErrorCode{}
ec := &ErrorCode{}
if err = s.doRequestPost(c, path, body, ec); err != nil {
return nil, err
return err
}
return
if ec.Errcode != Success {
return fmt.Errorf("errcode(%d), errmsg(%s)", ec.Errcode, ec.Errmsg)
}
return nil
}

// CSMessageSetTyping 下发客服当前输入状态给用户
// 注意:errcode = 0 为成功
// toUser:小程序用户的 OpenID
// typingStatus:枚举值:mini.TypingTyping、mini.TypingCancel
// 文档:https://developers.weixin.qq.com/miniprogram/dev/api-backend/open-api/customer-message/customerServiceMessage.setTyping.html
func (s *SDK) CSMessageSetTyping(c context.Context, toUser string, typingStatus TypingStatus) (ec *ErrorCode, err error) {
func (s *SDK) CSMessageSetTyping(c context.Context, toUser string, typingStatus TypingStatus) (err error) {
path := "/cgi-bin/message/custom/typing?access_token=" + s.Conf.AccessToken
body := make(bmap.BodyMap)
body.Set("touser", toUser)
Expand All @@ -65,11 +69,14 @@ func (s *SDK) CSMessageSetTyping(c context.Context, toUser string, typingStatus
case TypingCancel:
body.Set("command", "CancelTyping")
}
ec = &ErrorCode{}
ec := &ErrorCode{}
if err = s.doRequestPost(c, path, body, ec); err != nil {
return nil, err
return err
}
return
if ec.Errcode != Success {
return fmt.Errorf("errcode(%d), errmsg(%s)", ec.Errcode, ec.Errmsg)
}
return nil
}

// CSMessageUploadTempMedia 把媒体文件上传到微信服务器
Expand All @@ -85,5 +92,8 @@ func (s *SDK) CSMessageUploadTempMedia(c context.Context, img *util.File) (media
if err = s.doRequestPostFile(c, path, body, media); err != nil {
return nil, err
}
return
if media.Errcode != Success {
return nil, fmt.Errorf("errcode(%d), errmsg(%s)", media.Errcode, media.Errmsg)
}
return media, nil
}
6 changes: 5 additions & 1 deletion mini/login.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package mini

import (
"context"
"fmt"
)

// Code2Session 登录凭证校验
Expand All @@ -14,5 +15,8 @@ func (s *SDK) Code2Session(c context.Context, wxCode string) (session *Code2Sess
if err = s.doRequestGet(c, path, session); err != nil {
return nil, err
}
return
if session.Errcode != Success {
return nil, fmt.Errorf("errcode(%d), errmsg(%s)", session.Errcode, session.Errmsg)
}
return session, nil
}
2 changes: 2 additions & 0 deletions mini/model.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@ package mini
import "github.com/go-pay/wechat-sdk/pkg/xtime"

const (
Success = 0

DebugOff = 0
DebugOn = 1

Expand Down
12 changes: 8 additions & 4 deletions mini/uniform_message.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package mini

import (
"context"
"fmt"

"github.com/go-pay/wechat-sdk/pkg/bmap"
)
Expand All @@ -11,14 +12,17 @@ import (
// toUser:用户openid,可以是小程序的openid,也可以是mp_template_msg.appid对应的公众号的openid
// mpMsg:对应 mp_template_msg 的value值,BodyMap key-value 格式传入
// 文档:https://developers.weixin.qq.com/miniprogram/dev/api-backend/open-api/uniform-message/uniformMessage.send.html
func (s *SDK) UniformMessageSend(c context.Context, toUser string, mpMsg bmap.BodyMap) (ec *ErrorCode, err error) {
func (s *SDK) UniformMessageSend(c context.Context, toUser string, mpMsg bmap.BodyMap) (err error) {
path := "/cgi-bin/message/wxopen/template/uniform_send?access_token=" + s.Conf.AccessToken
body := make(bmap.BodyMap)
body.Set("touser", toUser)
body.Set("mp_template_msg", mpMsg)
ec = &ErrorCode{}
ec := &ErrorCode{}
if err = s.doRequestPost(c, path, body, ec); err != nil {
return nil, err
return err
}
return
if ec.Errcode != Success {
return fmt.Errorf("errcode(%d), errmsg(%s)", ec.Errcode, ec.Errmsg)
}
return nil
}
16 changes: 13 additions & 3 deletions mini/user_info.go
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import (
"context"
"crypto/sha256"
"encoding/hex"
"fmt"

"github.com/go-pay/wechat-sdk/pkg/bmap"
)
Expand All @@ -19,7 +20,10 @@ func (s *SDK) GetPaidUnionid(c context.Context, openid, transactionId string) (u
if err = s.doRequestGet(c, path, unionid); err != nil {
return nil, err
}
return
if unionid.Errcode != Success {
return nil, fmt.Errorf("errcode(%d), errmsg(%s)", unionid.Errcode, unionid.Errmsg)
}
return unionid, nil
}

// GetPaidUnionidByTradeNo 用户支付完成后,获取该用户的 UnionId,无需用户授权
Expand All @@ -34,7 +38,10 @@ func (s *SDK) GetPaidUnionidByTradeNo(c context.Context, openid, mchid, tradeNo
if err = s.doRequestGet(c, path, unionid); err != nil {
return nil, err
}
return
if unionid.Errcode != Success {
return nil, fmt.Errorf("errcode(%d), errmsg(%s)", unionid.Errcode, unionid.Errmsg)
}
return unionid, nil
}

// CheckEncryptedData 检查加密信息是否由微信生成
Expand All @@ -52,5 +59,8 @@ func (s *SDK) CheckEncryptedData(c context.Context, encryptedData string) (resul
if err = s.doRequestPost(c, path, body, result); err != nil {
return nil, err
}
return
if result.Errcode != Success {
return nil, fmt.Errorf("errcode(%d), errmsg(%s)", result.Errcode, result.Errmsg)
}
return result, nil
}
Loading

0 comments on commit 5603048

Please sign in to comment.