// Copyright 2019 Drone.IO Inc. All rights reserved. // Use of this source code is governed by the Drone Non-Commercial License // that can be found in the LICENSE file. package token import ( "context" "time" "github.com/drone/drone/core" "github.com/drone/go-scm/scm" "github.com/drone/go-scm/scm/transport/oauth2" ) // expiryDelta determines how earlier a token should be considered // expired than its actual expiration time. It is used to avoid late // expirations due to client-server time mismatches. const expiryDelta = time.Minute type renewer struct { refresh *oauth2.Refresher users core.UserStore } // Renewer returns a new Renewer. func Renewer(refresh *oauth2.Refresher, store core.UserStore) core.Renewer { return &renewer{ refresh: refresh, users: store, } } func (r *renewer) Renew(ctx context.Context, user *core.User, force bool) error { if r.refresh == nil { return nil } t := &scm.Token{ Token: user.Token, Refresh: user.Refresh, Expires: time.Unix(user.Expiry, 0), } if expired(t) == false && force == false { return nil } err := r.refresh.Refresh(t) if err != nil { return err } user.Token = t.Token user.Refresh = t.Refresh user.Expiry = t.Expires.Unix() return r.users.Update(ctx, user) } // expired reports whether the token is expired. func expired(token *scm.Token) bool { if len(token.Refresh) == 0 { return false } if token.Expires.IsZero() && len(token.Token) != 0 { return false } return token.Expires.Add(-expiryDelta). Before(time.Now()) }