From a083502d6c1e85d6522513a769ed0f1dd5c96e3b Mon Sep 17 00:00:00 2001 From: Aaron Torres Date: Wed, 29 Mar 2017 15:44:24 -0700 Subject: [PATCH] Adding the option to retain refresh/access token after successfully refreshing a token --- access.go | 2 +- access_test.go | 54 ++++++++++++++++++++++++++++++++++++++++++++++++++ config.go | 5 +++++ 3 files changed, 60 insertions(+), 1 deletion(-) diff --git a/access.go b/access.go index 14f3c36..3871b8c 100644 --- a/access.go +++ b/access.go @@ -507,7 +507,7 @@ func (s *Server) FinishAccessRequest(w *Response, r *http.Request, ar *AccessReq } // remove previous access token - if ret.AccessData != nil { + if ret.AccessData != nil && !s.Config.RetainTokenAfterRefresh { if ret.AccessData.RefreshToken != "" { w.Storage.RemoveRefresh(ret.AccessData.RefreshToken) } diff --git a/access_test.go b/access_test.go index 750cc0e..def71e8 100644 --- a/access_test.go +++ b/access_test.go @@ -77,9 +77,63 @@ func TestAccessRefreshToken(t *testing.T) { ar.Authorized = true server.FinishAccessRequest(resp, req, ar) } + //fmt.Printf("%+v", resp) + + if _, err := server.Storage.LoadRefresh("r9999"); err == nil { + t.Fatalf("token was not deleted") + } + + if resp.IsError && resp.InternalError != nil { + t.Fatalf("Error in response: %s", resp.InternalError) + } + + if resp.IsError { + t.Fatalf("Should not be an error") + } + + if resp.Type != DATA { + t.Fatalf("Response should be data") + } + + if d := resp.Output["access_token"]; d != "1" { + t.Fatalf("Unexpected access token: %s", d) + } + + if d := resp.Output["refresh_token"]; d != "r1" { + t.Fatalf("Unexpected refresh token: %s", d) + } +} +func TestAccessRefreshTokenSaveToken(t *testing.T) { + sconfig := NewServerConfig() + sconfig.AllowedAccessTypes = AllowedAccessType{REFRESH_TOKEN} + server := NewServer(sconfig, NewTestingStorage()) + server.AccessTokenGen = &TestingAccessTokenGen{} + server.Config.RetainTokenAfterRefresh = true + resp := server.NewResponse() + + req, err := http.NewRequest("POST", "http://localhost:14000/appauth", nil) + if err != nil { + t.Fatal(err) + } + req.SetBasicAuth("1234", "aabbccdd") + + req.Form = make(url.Values) + req.Form.Set("grant_type", string(REFRESH_TOKEN)) + req.Form.Set("refresh_token", "r9999") + req.Form.Set("state", "a") + req.PostForm = make(url.Values) + + if ar := server.HandleAccessRequest(resp, req); ar != nil { + ar.Authorized = true + server.FinishAccessRequest(resp, req, ar) + } //fmt.Printf("%+v", resp) + if _, err := server.Storage.LoadRefresh("r9999"); err != nil { + t.Fatalf("token incorrectly deleted: %s", err.Error()) + } + if resp.IsError && resp.InternalError != nil { t.Fatalf("Error in response: %s", resp.InternalError) } diff --git a/config.go b/config.go index 5b8929e..eccc16c 100644 --- a/config.go +++ b/config.go @@ -60,6 +60,10 @@ type ServerConfig struct { // Separator to support multiple URIs in Client.GetRedirectUri(). // If blank (the default), don't allow multiple URIs. RedirectUriSeparator string + + // RetainTokenAfter Refresh allows the server to retain the access and + // refresh token for re-use - default false + RetainTokenAfterRefresh bool } // NewServerConfig returns a new ServerConfig with default configuration @@ -73,5 +77,6 @@ func NewServerConfig() *ServerConfig { ErrorStatusCode: 200, AllowClientSecretInParams: false, AllowGetAccessRequest: false, + RetainTokenAfterRefresh: false, } }