package dingtalk import ( "ai_scheduler/internal/config" "ai_scheduler/internal/data/constants" "ai_scheduler/internal/pkg/l_request" "context" "encoding/json" "errors" "net/http" "time" "github.com/redis/go-redis/v9" ) type Auth struct { redis *redis.Client cfg *config.Config } func NewAuth(cfg *config.Config, redis *redis.Client) *Auth { return &Auth{ redis: redis, cfg: cfg, } } func (a *Auth) GetAccessToken(ctx context.Context, clientId string, clientSecret string) (accessToken string, err error) { if clientId == "" { return "", errors.New("clientId is empty") } token := a.redis.Get(ctx, a.getKey(clientId)).String() if token == "" { authInfo, _err := a.getNewAccessToken(ctx, clientId, clientSecret) if _err != nil { return "", _err } a.redis.SetEx(ctx, a.getKey(clientId), authInfo.AccessToken, time.Duration(authInfo.ExpiresIn-3600)*time.Second) accessToken = authInfo.AccessToken } return } func (a *Auth) getKey(clientId string) string { return a.cfg.Redis.Key + ":" + constants.DingTalkAuthBaseKeyPrefix + ":" + clientId } func (a *Auth) getNewAccessToken(ctx context.Context, clientId string, clientSecret string) (auth AuthInfo, err error) { if clientId == "" || clientSecret == "" { err = errors.New("clientId or clientSecret is empty") return } req := l_request.Request{ Method: http.MethodPost, Url: constants.GetDingTalkRequestUrl(constants.RequestUrlGetAccessToken, nil), Data: map[string]string{ "appkey": clientId, "appsecret": clientSecret, }, } res, err := req.Send() if err != nil { return } err = json.Unmarshal(res.Content, &auth) return }