mirror of
https://github.com/silenceper/wechat.git
synced 2026-02-04 12:52:27 +08:00
F ix work access token (#810)
* feat: enhance WorkAccessToken to include AgentID for improved token management - Added AgentID field to WorkAccessToken struct. - Updated NewWorkAccessToken function to accept AgentID as a parameter. - Modified access token cache key to incorporate AgentID, ensuring unique cache entries per agent. This change improves the handling of access tokens in a multi-agent environment. * refactor: enhance WorkAccessToken to improve cache key handling - Updated the AgentID field in WorkAccessToken struct to clarify its optional nature for distinguishing applications. - Modified the access token cache key construction to support both new and legacy formats based on the presence of AgentID. - Added comments for better understanding of the cache key logic and its compatibility with historical versions. This change improves the flexibility and clarity of access token management in multi-agent scenarios. * feat: enhance WorkAccessToken with new constructor for AgentID support - Introduced NewWorkAccessTokenWithAgentID function to maintain backward compatibility while allowing for AgentID usage. - Updated NewWorkAccessToken to call the new constructor, ensuring seamless integration. - Improved error handling in GetAccessTokenContext by checking for cache availability and handling potential errors during cache operations. This change enhances the flexibility of access token management, particularly in multi-agent scenarios, while ensuring compatibility with existing implementations.
This commit is contained in:
@@ -189,19 +189,27 @@ func (ak *StableAccessToken) GetAccessTokenDirectly(ctx context.Context, forceRe
|
|||||||
type WorkAccessToken struct {
|
type WorkAccessToken struct {
|
||||||
CorpID string
|
CorpID string
|
||||||
CorpSecret string
|
CorpSecret string
|
||||||
|
AgentID string // 可选,用于区分不同应用
|
||||||
cacheKeyPrefix string
|
cacheKeyPrefix string
|
||||||
cache cache.Cache
|
cache cache.Cache
|
||||||
accessTokenLock *sync.Mutex
|
accessTokenLock *sync.Mutex
|
||||||
}
|
}
|
||||||
|
|
||||||
// NewWorkAccessToken new WorkAccessToken
|
// NewWorkAccessToken new WorkAccessToken (保持向后兼容)
|
||||||
func NewWorkAccessToken(corpID, corpSecret, cacheKeyPrefix string, cache cache.Cache) AccessTokenContextHandle {
|
func NewWorkAccessToken(corpID, corpSecret, agentID, cacheKeyPrefix string, cache cache.Cache) AccessTokenContextHandle {
|
||||||
|
// 调用新方法,保持兼容性
|
||||||
|
return NewWorkAccessTokenWithAgentID(corpID, corpSecret, agentID, cacheKeyPrefix, cache)
|
||||||
|
}
|
||||||
|
|
||||||
|
// NewWorkAccessTokenWithAgentID new WorkAccessToken with agentID
|
||||||
|
func NewWorkAccessTokenWithAgentID(corpID, corpSecret, agentID, cacheKeyPrefix string, cache cache.Cache) AccessTokenContextHandle {
|
||||||
if cache == nil {
|
if cache == nil {
|
||||||
panic("cache the not exist")
|
panic("cache is needed")
|
||||||
}
|
}
|
||||||
return &WorkAccessToken{
|
return &WorkAccessToken{
|
||||||
CorpID: corpID,
|
CorpID: corpID,
|
||||||
CorpSecret: corpSecret,
|
CorpSecret: corpSecret,
|
||||||
|
AgentID: agentID,
|
||||||
cache: cache,
|
cache: cache,
|
||||||
cacheKeyPrefix: cacheKeyPrefix,
|
cacheKeyPrefix: cacheKeyPrefix,
|
||||||
accessTokenLock: new(sync.Mutex),
|
accessTokenLock: new(sync.Mutex),
|
||||||
@@ -218,7 +226,17 @@ func (ak *WorkAccessToken) GetAccessTokenContext(ctx context.Context) (accessTok
|
|||||||
// 加上lock,是为了防止在并发获取token时,cache刚好失效,导致从微信服务器上获取到不同token
|
// 加上lock,是为了防止在并发获取token时,cache刚好失效,导致从微信服务器上获取到不同token
|
||||||
ak.accessTokenLock.Lock()
|
ak.accessTokenLock.Lock()
|
||||||
defer ak.accessTokenLock.Unlock()
|
defer ak.accessTokenLock.Unlock()
|
||||||
accessTokenCacheKey := fmt.Sprintf("%s_access_token_%s", ak.cacheKeyPrefix, ak.CorpID)
|
|
||||||
|
// 构建缓存key
|
||||||
|
var accessTokenCacheKey string
|
||||||
|
if ak.AgentID != "" {
|
||||||
|
// 如果设置了AgentID,使用新的key格式
|
||||||
|
accessTokenCacheKey = fmt.Sprintf("%s_access_token_%s_%s", ak.cacheKeyPrefix, ak.CorpID, ak.AgentID)
|
||||||
|
} else {
|
||||||
|
// 兼容历史版本的key格式
|
||||||
|
accessTokenCacheKey = fmt.Sprintf("%s_access_token_%s", ak.cacheKeyPrefix, ak.CorpID)
|
||||||
|
}
|
||||||
|
|
||||||
val := ak.cache.Get(accessTokenCacheKey)
|
val := ak.cache.Get(accessTokenCacheKey)
|
||||||
if val != nil {
|
if val != nil {
|
||||||
accessToken = val.(string)
|
accessToken = val.(string)
|
||||||
@@ -234,6 +252,9 @@ func (ak *WorkAccessToken) GetAccessTokenContext(ctx context.Context) (accessTok
|
|||||||
|
|
||||||
expires := resAccessToken.ExpiresIn - 1500
|
expires := resAccessToken.ExpiresIn - 1500
|
||||||
err = ak.cache.Set(accessTokenCacheKey, resAccessToken.AccessToken, time.Duration(expires)*time.Second)
|
err = ak.cache.Set(accessTokenCacheKey, resAccessToken.AccessToken, time.Duration(expires)*time.Second)
|
||||||
|
if err != nil {
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
accessToken = resAccessToken.AccessToken
|
accessToken = resAccessToken.AccessToken
|
||||||
return
|
return
|
||||||
|
|||||||
@@ -12,7 +12,6 @@ type Config struct {
|
|||||||
AgentID string `json:"agent_id"` // agent_id
|
AgentID string `json:"agent_id"` // agent_id
|
||||||
Cache cache.Cache
|
Cache cache.Cache
|
||||||
RasPrivateKey string // 消息加密私钥,可以在企业微信管理端--管理工具--消息加密公钥查看对用公钥,私钥一般由自己保存
|
RasPrivateKey string // 消息加密私钥,可以在企业微信管理端--管理工具--消息加密公钥查看对用公钥,私钥一般由自己保存
|
||||||
|
|
||||||
Token string `json:"token"` // 微信客服回调配置,用于生成签名校验回调请求的合法性
|
Token string `json:"token"` // 微信客服回调配置,用于生成签名校验回调请求的合法性
|
||||||
EncodingAESKey string `json:"encoding_aes_key"` // 微信客服回调p配置,用于解密回调消息内容对应的密文
|
EncodingAESKey string `json:"encoding_aes_key"` // 微信客服回调p配置,用于解密回调消息内容对应的密文
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ func NewClient(cfg *config.Config) (client *Client, err error) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// 初始化 AccessToken Handle
|
// 初始化 AccessToken Handle
|
||||||
defaultAkHandle := credential.NewWorkAccessToken(cfg.CorpID, cfg.CorpSecret, credential.CacheKeyWorkPrefix, cfg.Cache)
|
defaultAkHandle := credential.NewWorkAccessToken(cfg.CorpID, cfg.CorpSecret, cfg.AgentID, credential.CacheKeyWorkPrefix, cfg.Cache)
|
||||||
ctx := &context.Context{
|
ctx := &context.Context{
|
||||||
Config: cfg,
|
Config: cfg,
|
||||||
AccessTokenHandle: defaultAkHandle,
|
AccessTokenHandle: defaultAkHandle,
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ type Work struct {
|
|||||||
|
|
||||||
// NewWork init work
|
// NewWork init work
|
||||||
func NewWork(cfg *config.Config) *Work {
|
func NewWork(cfg *config.Config) *Work {
|
||||||
defaultAkHandle := credential.NewWorkAccessToken(cfg.CorpID, cfg.CorpSecret, credential.CacheKeyWorkPrefix, cfg.Cache)
|
defaultAkHandle := credential.NewWorkAccessToken(cfg.CorpID, cfg.CorpSecret, cfg.AgentID, credential.CacheKeyWorkPrefix, cfg.Cache)
|
||||||
ctx := &context.Context{
|
ctx := &context.Context{
|
||||||
Config: cfg,
|
Config: cfg,
|
||||||
AccessTokenHandle: defaultAkHandle,
|
AccessTokenHandle: defaultAkHandle,
|
||||||
|
|||||||
Reference in New Issue
Block a user