Невозможно получить Oauth2 TokenSource для обновления токена, полученного из хранилища - PullRequest
0 голосов
/ 24 октября 2019

После того, как пользователь авторизует Календарь Google, служба NodeJS сохраняет коды , 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 Ответ на неверный запрос: {"error": "invalid_grant", "error_description": "Неверный код авторизации". }

    tok, err := config.Exchange(context.TODO(), in)
if err != nil {
    log.Fatalf("Unable to retrieve token from web: %v", err)
}

Попытка доступа с использованием календаря. 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

}

1 Ответ

0 голосов
/ 26 октября 2019

Это была проблема Unmarshalling.

При сохранении токена из Node он сериализует время истечения как "expiry_date" , а Go Token имеет представление json просто "expiry" . Устранение остальной части объекта в объект oauth2.Token и добавление времени истечения этого объекта решило проблему.

...