用户授权Google日历后,NodeJS服务将Code,AccessToken和RefreshToken保存到存储中。
[尝试使用相同的令牌通过Go编写的不同后端服务访问用户的日历。当AccessToken有效时,数据是可访问的,但是当AccessToken过期时,在尝试访问事件时,即使该令牌有效,也无法获取config.Exchange()或config.TokenSource()给出一个有效的新令牌。 ,出现错误:
错误401:无效的凭据,authError退出状态1
tok, err := config.TokenSource(ctx, token).Token() // token is previous valid token
if err != nil {
log.Fatalf("Unable to retrieve token from web: %v", err)
}
也试图用代码交换新令牌但无济于事
400错误的请求回应:{“错误”:“ invalid_grant”,“ error_description”:“验证码格式错误。”}
tok, err := config.Exchange(context.TODO(), in)
if err != nil {
log.Fatalf("Unable to retrieve token from web: %v", err)
}
尝试使用calendar.NewService访问
srv, _ := calendar.NewService(ctx, option.WithTokenSource(config.TokenSource(ctx, tok)))
如何获得无需用户干预即可从其他服务脱机访问的令牌?
更新:将令牌存储到Redis-RedisJSON,但仍然不会获得新的AccessToken。这是我要传递有效令牌的完整功能。它仅在AccessToken到期之前起作用。
func GetGoogleCalendarEvents(token *oauth2.Token, userid string) *calendar.Events {
tok := &oauth2.Token{}
var config *oauth2.Config
ctx := context.Background()
b, err := ioutil.ReadFile("credentials.json")
if err != nil {
log.Fatalf("Unable to read client secret file: %v", err)
}
config, err = google.ConfigFromJSON(b, calendar.CalendarScope) //calendar.CalendarScope)
if err != nil {
log.Fatalf("Unable to parse client secret file to config: %v", err)
}
tok = token
if token.Expiry.Before(time.Now()) {
tokenSource := config.TokenSource(ctx, token) //oauth2.NoContext
newToken, err := tokenSource.Token()
if err != nil {
log.Fatalln(err)
}
if tok.AccessToken != newToken.AccessToken {
SetAuthCredToCache(userid, tok)
tok = newToken
fmt.Println(newToken)
}
}
fmt.Println(tok.Expiry, tok.Valid(), tok.Type(), tok.RefreshToken, tok.TokenType)
srv, _ := calendar.NewService(ctx, option.WithTokenSource(config.TokenSource(ctx, tok)))
t := time.Now().Format(time.RFC3339)
events, err := srv.Events.List("primary").ShowDeleted(true).
SingleEvents(true).TimeMin(t).OrderBy("startTime").Do()
if err != nil {
log.Fatalf("Unable to retrieve next ten of the user's events: %v", err)
}
return events
}
这是一个编组问题。
从节点保存令牌时,它将到期时间序列化为“ expiry_date”,而Go Token的json表示形式仅为“ expiry”。将其余对象解组到oauth2.Token对象,并向该对象添加到期时间即可解决该问题。