github.com/cloudfoundry-attic/cli-with-i18n@v6.32.1-0.20171002233121-7401370d3b85+incompatible/api/cloudcontroller/wrapper/uaa_authentication.go (about) 1 package wrapper 2 3 import ( 4 "code.cloudfoundry.org/cli/api/cloudcontroller" 5 "code.cloudfoundry.org/cli/api/cloudcontroller/ccerror" 6 "code.cloudfoundry.org/cli/api/uaa" 7 ) 8 9 //go:generate counterfeiter . UAAClient 10 11 // UAAClient is the interface for getting a valid access token 12 type UAAClient interface { 13 RefreshAccessToken(refreshToken string) (uaa.RefreshedTokens, error) 14 } 15 16 //go:generate counterfeiter . TokenCache 17 18 // TokenCache is where the UAA token information is stored. 19 type TokenCache interface { 20 AccessToken() string 21 RefreshToken() string 22 SetAccessToken(token string) 23 SetRefreshToken(token string) 24 } 25 26 // UAAAuthentication wraps connections and adds authentication headers to all 27 // requests 28 type UAAAuthentication struct { 29 connection cloudcontroller.Connection 30 client UAAClient 31 cache TokenCache 32 } 33 34 // NewUAAAuthentication returns a pointer to a UAAAuthentication wrapper with 35 // the client and a token cache. 36 func NewUAAAuthentication(client UAAClient, cache TokenCache) *UAAAuthentication { 37 return &UAAAuthentication{ 38 client: client, 39 cache: cache, 40 } 41 } 42 43 // Wrap sets the connection on the UAAAuthentication and returns itself 44 func (t *UAAAuthentication) Wrap(innerconnection cloudcontroller.Connection) cloudcontroller.Connection { 45 t.connection = innerconnection 46 return t 47 } 48 49 // SetClient sets the UAA client that the wrapper will use. 50 func (t *UAAAuthentication) SetClient(client UAAClient) { 51 t.client = client 52 } 53 54 // Make adds authentication headers to the passed in request and then calls the 55 // wrapped connection's Make. If the client is not set on the wrapper, it will 56 // not add any header or handle any authentication errors. 57 func (t *UAAAuthentication) Make(request *cloudcontroller.Request, passedResponse *cloudcontroller.Response) error { 58 if t.client == nil { 59 return t.connection.Make(request, passedResponse) 60 } 61 62 request.Header.Set("Authorization", t.cache.AccessToken()) 63 64 requestErr := t.connection.Make(request, passedResponse) 65 if _, ok := requestErr.(ccerror.InvalidAuthTokenError); ok { 66 tokens, err := t.client.RefreshAccessToken(t.cache.RefreshToken()) 67 if err != nil { 68 return err 69 } 70 71 t.cache.SetAccessToken(tokens.AuthorizationToken()) 72 t.cache.SetRefreshToken(tokens.RefreshToken) 73 74 if request.Body != nil { 75 err = request.ResetBody() 76 if err != nil { 77 if _, ok := err.(ccerror.PipeSeekError); ok { 78 return ccerror.PipeSeekError{Err: requestErr} 79 } 80 return err 81 } 82 } 83 request.Header.Set("Authorization", t.cache.AccessToken()) 84 requestErr = t.connection.Make(request, passedResponse) 85 } 86 87 return requestErr 88 }