wxapi

package module
v0.5.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Nov 8, 2020 License: MIT Imports: 9 Imported by: 0

README

微信公众号开发SDK

go-wx-api是对微信公众号API的封装,可以当作SDK使用,主要特点:

  • 对常用消息、事件的接收和回复做了封装,已经无需了解相关的公众号开发文档;见使用方法1;
  • 提供了缺省的消息、事件处理方法,可以根据实际需求覆盖相关实现;见使用方法2;
  • 使用go-wx-api可以同时支持多个公众号;见使用方法3;
  • 菜单点击后允许进入自己的页面,go-wx-api提供了统一的入口进入菜单处理,获取用户openId, 根据state参数进入具体业务处理。可以通过提供菜单跳转处理器实现具体业务;见使用方法1;
  • go-wx-gateway是使用go-wx-api实现的微信公众号网关服务, 通过go-wx-gateway,就可以把微信公众号服务的开发转化为普通web服务开发。

编译例子

  1. 该函数包已经使用go modules发布,需要golang 1.11.x及以上版本
  2. 请参考go-wx-apps,那里包含了例程和工具程序

使用方法1: (实现消息处理器、菜单跳转处理器的例子)

go-wx-api已经对公众号常用的消息(文本框架输入、发语音等)、事件(用户关注、点击菜单等)做了提取和封装处理。缺省处理对消息、事件做了简单的应答处理,缺省处理除了能给公众号管理后台做开发者设置功能外,没有实际意义。具体业务可以根据需要对go-wx-api的消息处理器接口进行实现:

  1. 消息处理器的定义和实现

    import (
        "github.com/rosbit/go-wx-api/msg"
        "fmt"
    )
    
    // 消息处理器定义
    type YourMsgHandler struct {
        wxmsg.WxMsgHandlerAdapter  // 包含了所有消息、事件的缺省实现
    }
    
    // 接口定义见 wxmsg.WxMsgHandler,根据需要选择实现其中的方法
    
    // 文本消息处理
    func (h *YourMsgHandler) HandleTextMsg(textMsg *wxmsg.TextMsg) wxmsg.ReplyMsg {
        return NewReplyTextMsg(textMsg.FromUserName, textMsg.ToUserName, fmt.Sprintf("收到了消息:%s", textMsg.Content))
    }
    
    // 用户关注公众号处理
    func (h *YourMsgHandler) HandleSubscribeEvent(subscribeEvent *wxmsg.SubscribeEvent) wxmsg.ReplyMsg {
        return wxmsg.NewReplyTextMsg(subscribeEvent.FromUserName, subscribeEvent.ToUserName, "welcome")
    }
    
  2. 注册消息处理器

    • 单一公众号注册方法见方法2
    • 多公众号注册方法见方法3

使用方法2: (单一公众号服务)

以下是一个简单的例子,用于说明使用go-wx-api的主要执行步骤。更详细的例子参考go-wx-apps

package main

import (
	"github.com/rosbit/go-wx-api/conf"
	"github.com/rosbit/go-wx-api"
	"net/http"
	"fmt"
)

const (
	token     = "微信公众号的token"
	appId     = "微信公众号appId"
	appSecret = "微信公众号的secret"
	aesKey    = "" //安全模式 使用的AESKey,如果是 明文传输,该串为空
	
	listenPort = 7070   // 服务侦听的端口号,请根据微信公众号管理端的服务器配置正确设置
	service    = "/wx"  // 微信公众号管理端服务器配置中URL的路径部分

	workerNum = 3 // 处理请求的并发数
)

func main() {
	// 步骤1. 设置配置参数
	if err := wxconf.SetParams(token, appId, appSecret, aesKey); err != nil {
		fmt.Printf("failed to set params: %v\n", err)
		return
	}

	// 步骤2. 初始化SDK
	wxapi.InitWxAPI(workerNum, os.Stdout)

	// 注册消息处理器、菜单跳转处理器。如果没有相应的实现,可以注释掉下面两行代码
	wxapi.RegisterWxMsghandler(&YourMsgHandler{})

	// 菜单跳转全权交给另外一个URL处理
	// redirectURL接收POST请求,POST body是一个JSON: {"appId":"xxx", "openId", "xxx", "state": "xxx", "userInfo": {}}
	// 它可以随意处理HTTP请求、输出HTTP响应,响应结果直接返回公众号浏览器
	wxapi.RegisterRedirectUrl("http://youhost.com/path/to/redirect")

	// 步骤2.5 设置签名验证的中间件。由于net/http不支持中间件,省去该步骤
	// signatureChecker := wxapi.NewWxSignatureChecker(wxconf.WxParams.Token, 0, []string{service})
	// <middleWareContainer>.Use(signatureChecker)

	// 步骤3. 设置http路由,启动http服务
	http.HandleFunc(service, wxapi.Echo)     // 用于配置
	http.HandleFunc(service, wxapi.Request)  // 用于实际执行公众号请求,和wxapi.Echo只能使用一个。
	                                         // 可以使用支持高级路由功能的web框架同时设置,参考 github.com/rosbit/go-wx-api/samples/wx-echo-server
	http.ListenAndServe(fmt.Sprintf(":%d", listenPort), nil)
}

使用方法3: (多个公众号服务)

以下代码仅仅为同时启用公众号的示例:

package main

import (
	"github.com/rosbit/go-wx-api/conf"
	"github.com/rosbit/go-wx-api"
	"net/http"
	"fmt"
)

type WxConf struct {
	token string
	appId string
	appSecret string
	aesKey string
	workerNum int
	service string
}

var (
	listenPort = 7070   // 服务侦听的端口号,请根据微信公众号管理端的服务器配置正确设置
	wxServices = []WxConf{
		WxConf{
			token: "微信公众号1的token",
			appId: "微信公众号1的appId",
			appSecret: "微信公众号的1secret",
			aesKey: "",      // 安全模式 使用的AESKey,如果是 明文传输,该串为空
			workerNum: 3,    // 处理请求的并发数
			service: "/wx1", // 微信公众号管理端服务器配置中URL的路径部分
		},
		WxConf{
			token: "微信公众号2的token",
			appId: "微信公众号2的appId",
			appSecret: "微信公众号2的secret",
			aesKey: "",      // 安全模式 使用的AESKey,如果是 明文传输,该串为空
			workerNum: 3,    // 处理请求的并发数
			service: "/wx2", // 微信公众号管理端服务器配置中URL的路径部分
		},
		// 其它服务号
	}
)

func main() {
	// 对于每一个公众号执行
	for _, conf := range wxServices {
		// 步骤1. 设置配置参数
		wxParams, err := wxconf.NewWxParams(conf.token, conf.appId, conf.appSecret, conf.aesKey)
		if err != nil {
			fmt.Printf("failed to set params: %v\n", err)
			return
		}

		// 步骤2. 初始化SDK
		wxService := wxapi.InitWxAPIWithParams(wxParams, conf.workerNum, os.Stdout)

		// 注册消息处理器、菜单跳转处理器。如果没有相应的实现,可以注释掉下面两行代码
		wxService.RegisterWxMsghandler(&YourMsgHandler{})   // 不同的wxService可以有不同的MsgHandler

		// 菜单跳转全权交给另外一个URL处理
		// redirectURL接收POST请求,POST body是一个JSON: {"appId":"xxx", "openId", "xxx", "state": "xxx", "userInfo": {}}
		// 它可以随意处理HTTP请求、输出HTTP响应,响应结果直接返回公众号浏览器
		wxService.RegisterRedirectUrl("http://yourhost.com/path/to/redirect")

		// 步骤2.5 设置签名验证的中间件。由于net/http不支持中间件,省去该步骤
		// signatureChecker := wxapi.NewWxSignatureChecker(wxParams.Token, 0, []string{conf.service})
		// <middleWareContainer>.Use(signatureChecker)

		// 步骤3. 设置http路由,启动http服务
		http.HandleFunc(conf.service, wxService.Echo)     // 用于配置
		http.HandleFunc(conf.service, wxService.Request)  // 用于实际执行公众号请求,和wxService.Echo只能使用一个。
		                                                  // 可以使用支持高级路由功能的web框架同时设置
	}

	http.ListenAndServe(fmt.Sprintf(":%d", listenPort), nil)
}

其它

  1. 该函数包可以处理文本消息、用户关注/取消关注事件、菜单点击事件
  2. 其它消息、事件可以根据需要扩充

Documentation

Overview

*

  • RESTful API implementation
  • GET /wx -- 用于实现服务号接口配置,实际路径通过http路由关联
  • POST /wx -- 处理微信消息/事件的入口,实际路径通过http路由关联
  • GET /redirect -- 微信网页授权接口,处理服务号菜单的总入口,
  • 不同菜单通过网页授权参数state区分,实际路径通过http路由关联
  • Rosbit Xu

*

  • 注册微信消息/事件处理器,用于覆盖缺省处理器

*

  • signature checker as a http middleware
  • Rosbit Xu

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

func Echo

func Echo(w http.ResponseWriter, r *http.Request)

用于微信服务号设置

func InitWxAPI

func InitWxAPI(workerNum int, logger io.Writer)

func NewWxSignatureChecker

func NewWxSignatureChecker(wxToken string, timeout int, uriPrefixes []string) func(http.ResponseWriter, *http.Request, http.HandlerFunc)

*

  • 创建http处理中间件,验证消息签名,如果非法直接返回错误
  • @param wxToken 公众号在微信管理后台定义的token
  • @param timeout 消息时间戳超时处理,秒数,如果<=0不检查时间戳
  • @param uriPrefixes 需要检查签名的URI前缀列表,不相关的URI忽略检查;如果为nil,全部检查

func Redirect

func Redirect(w http.ResponseWriter, r *http.Request)

微信网页授权

func RegisterRedictHandler

func RegisterRedictHandler(handler RedirectHandler)

*

  • @deprecated,建议使用RegisterRedirectUrl()
  • 注册微信网页授权处理函数

func RegisterRedirectUrl added in v0.4.0

func RegisterRedirectUrl(redirectUrl string, userInfoFlag ...string)

注册转发HTTP(s) URL,该URL将全权决定网页授权的处理。如果该URL存在,优先级要"高于"RegisterRedictHandler()注册函数。 参数JSON: {"appId": "xxx", "openId": "xxx", "state": "state"} 该URL的以POST形式接收参数,而且会得到所有的HTTP头信息,可以设置任何的响应头信息,响应结果直接显示在公众号浏览器中 响应时间要控制好,避免微信服务超时 userInfoFlag只取第一个,用于检查转发url中是否有标志串,表示使用 snsapi_userinfo 获取用户信息

func RegisterWxMsghandler added in v0.1.0

func RegisterWxMsghandler(msgHandler wxmsg.WxMsgHandler)

*

  • 注册消息/事件处理器
  • @msgHandler 消息处理器

func Request

func Request(w http.ResponseWriter, r *http.Request)

微信服务号消息/事件处理入口

Types

type RedirectHandler

type RedirectHandler = wxauth.RedirectHandlerWithoutAppId

*

  • @deprecated,建议使用RegisterRedirectUrl()
  • [函数签名]根据服务号菜单state做跳转
  • @param openId 订阅用户的openId
  • @param state 微信网页授权中的参数,用来标识某个菜单
  • @return
  • c 需要显示服务号对话框中的内容
  • h 需要在微信内嵌浏览器中设置的header信息,包括Cookie
  • r 需要通过302跳转的URL。如果r不是空串,c的内容被忽略
  • err 如果没有错误返回nil,非nil表示错误

type WxHandler added in v0.2.0

type WxHandler struct {
	// contains filtered or unexported fields
}

func InitWxAPIWithParams added in v0.2.0

func InitWxAPIWithParams(params *wxconf.WxParamsT, workerNum int, logger io.Writer) *WxHandler

func (*WxHandler) Echo added in v0.2.0

func (wx *WxHandler) Echo(w http.ResponseWriter, r *http.Request)

func (*WxHandler) Redirect added in v0.2.0

func (wx *WxHandler) Redirect(w http.ResponseWriter, r *http.Request)

func (*WxHandler) RegisterRedictHandler added in v0.2.0

func (h *WxHandler) RegisterRedictHandler(handler wxauth.RedirectHandler)

@deprecated,建议使用RegisterRedirectUrl()

func (*WxHandler) RegisterRedirectUrl added in v0.4.0

func (h *WxHandler) RegisterRedirectUrl(redirectUrl string, userInfoFlag ...string)

注册转发HTTP(s) URL,该URL将全权决定网页授权的处理。如果该URL存在,优先级要"高于"RegisterRedictHandler()注册函数。 参数JSON: {"appId": "xxx", "openId": "xxx", "state": "state"} 该URL的以POST形式接收参数,而且会得到所有的HTTP头信息,可以设置任何的响应头信息,响应结果直接显示在公众号浏览器中 响应时间要控制好,避免微信服务超时 userInfoFlag只取第一个,用于检查转发url中是否有标志串,表示使用 snsapi_userinfo 获取用户信息

func (*WxHandler) RegisterWxMsghandler added in v0.2.0

func (h *WxHandler) RegisterWxMsghandler(msgHandler wxmsg.WxMsgHandler)

---------------- 支持多服务号 ------------------

func (*WxHandler) Request added in v0.2.0

func (wx *WxHandler) Request(w http.ResponseWriter, r *http.Request)

Directories

Path Synopsis
* * 缺省的微信网页授权处理 * * 微信网页授权处理主流程:固定线程数处理所有的请求 * 工作方式: * 1.
* * 缺省的微信网页授权处理 * * 微信网页授权处理主流程:固定线程数处理所有的请求 * 工作方式: * 1.
* * 微信服务号配置信息
* * 微信服务号配置信息
* * 微信信息加解密/签名/随机数 * 1.
* * 微信信息加解密/签名/随机数 * 1.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL