|
28 | 28 | // ErrTokenInvalid is error for invalid token
|
29 | 29 | ErrTokenInvalid = errors.New("goic id_token: invalid id_token")
|
30 | 30 |
|
| 31 | + // ErrRefreshTokenInvalid is error for invalid token |
| 32 | + ErrRefreshTokenInvalid = errors.New("goic id_token: invalid refresh_token") |
| 33 | + |
31 | 34 | // ErrTokenClaims is error for invalid token claims
|
32 | 35 | ErrTokenClaims = errors.New("goic id_token: invalid id_token claims")
|
33 | 36 |
|
@@ -194,13 +197,17 @@ func (g *Goic) Authenticate(p *Provider, code, nonce, curl string) (*Token, erro
|
194 | 197 | }
|
195 | 198 |
|
196 | 199 | // getToken actually gets token from Provider via wellKnown.TokenURI
|
197 |
| -func (g *Goic) getToken(p *Provider, code, redir string) (*Token, error) { |
| 200 | +func (g *Goic) getToken(p *Provider, code, redir, grant string) (*Token, error) { |
198 | 201 | tok := &Token{Provider: p.Name}
|
199 | 202 |
|
200 | 203 | qry := url.Values{}
|
201 |
| - qry.Add("grant_type", "authorization_code") |
202 |
| - qry.Add("code", code) |
203 |
| - qry.Add("redirect_uri", redir) |
| 204 | + qry.Add("grant_type", grant) |
| 205 | + if grant == "authorization_code" { |
| 206 | + qry.Add("code", code) |
| 207 | + qry.Add("redirect_uri", redir) |
| 208 | + } else { |
| 209 | + qry.Add("refresh_token", code) |
| 210 | + } |
204 | 211 | qry.Add("client_id", p.clientID)
|
205 | 212 | qry.Add("client_secret", p.clientSecret)
|
206 | 213 |
|
@@ -390,6 +397,26 @@ func (g *Goic) UserInfo(tok *Token) *User {
|
390 | 397 | return user
|
391 | 398 | }
|
392 | 399 |
|
| 400 | +// RefreshToken gets new access token using the refresh token |
| 401 | +func (g *Goic) RefreshToken(tok *Token) (*Token, error) { |
| 402 | + name := tok.Provider |
| 403 | + if !g.Supports(name) { |
| 404 | + return nil, ErrProviderSupport |
| 405 | + } |
| 406 | + if tok.RefreshToken == "" { |
| 407 | + return nil, ErrRefreshTokenInvalid |
| 408 | + } |
| 409 | + |
| 410 | + p := g.providers[name] |
| 411 | + t, err := g.getToken(p, tok.RefreshToken, "", "refresh_token") |
| 412 | + if err == ErrTokenEmpty { |
| 413 | + err = nil |
| 414 | + } |
| 415 | + |
| 416 | + return t, err |
| 417 | +} |
| 418 | + |
| 419 | +// logIf logs if verbose is set |
393 | 420 | func (g *Goic) logIf(s string, v ...interface{}) {
|
394 | 421 | if g.verbose {
|
395 | 422 | log.Printf(s, v...)
|
|
0 commit comments