1 //go:build go1.13
2 // +build go1.13
3 4 // Copyright 2017 Microsoft Corporation
5 //
6 // Licensed under the Apache License, Version 2.0 (the "License");
7 // you may not use this file except in compliance with the License.
8 // You may obtain a copy of the License at
9 //
10 // http://www.apache.org/licenses/LICENSE-2.0
11 //
12 // Unless required by applicable law or agreed to in writing, software
13 // distributed under the License is distributed on an "AS IS" BASIS,
14 // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 // See the License for the specific language governing permissions and
16 // limitations under the License.
17 18 package adal
19 20 import (
21 "context"
22 "fmt"
23 "net/http"
24 "time"
25 )
26 27 func getMSIEndpoint(ctx context.Context, sender Sender) (*http.Response, error) {
28 tempCtx, cancel := context.WithTimeout(ctx, 2*time.Second)
29 defer cancel()
30 // http.NewRequestWithContext() was added in Go 1.13
31 req, _ := http.NewRequestWithContext(tempCtx, http.MethodGet, msiEndpoint, nil)
32 q := req.URL.Query()
33 q.Add("api-version", msiAPIVersion)
34 req.URL.RawQuery = q.Encode()
35 return sender.Do(req)
36 }
37 38 // EnsureFreshWithContext will refresh the token if it will expire within the refresh window (as set by
39 // RefreshWithin) and autoRefresh flag is on. This method is safe for concurrent use.
40 func (mt *MultiTenantServicePrincipalToken) EnsureFreshWithContext(ctx context.Context) error {
41 if err := mt.PrimaryToken.EnsureFreshWithContext(ctx); err != nil {
42 return fmt.Errorf("failed to refresh primary token: %w", err)
43 }
44 for _, aux := range mt.AuxiliaryTokens {
45 if err := aux.EnsureFreshWithContext(ctx); err != nil {
46 return fmt.Errorf("failed to refresh auxiliary token: %w", err)
47 }
48 }
49 return nil
50 }
51 52 // RefreshWithContext obtains a fresh token for the Service Principal.
53 func (mt *MultiTenantServicePrincipalToken) RefreshWithContext(ctx context.Context) error {
54 if err := mt.PrimaryToken.RefreshWithContext(ctx); err != nil {
55 return fmt.Errorf("failed to refresh primary token: %w", err)
56 }
57 for _, aux := range mt.AuxiliaryTokens {
58 if err := aux.RefreshWithContext(ctx); err != nil {
59 return fmt.Errorf("failed to refresh auxiliary token: %w", err)
60 }
61 }
62 return nil
63 }
64 65 // RefreshExchangeWithContext refreshes the token, but for a different resource.
66 func (mt *MultiTenantServicePrincipalToken) RefreshExchangeWithContext(ctx context.Context, resource string) error {
67 if err := mt.PrimaryToken.RefreshExchangeWithContext(ctx, resource); err != nil {
68 return fmt.Errorf("failed to refresh primary token: %w", err)
69 }
70 for _, aux := range mt.AuxiliaryTokens {
71 if err := aux.RefreshExchangeWithContext(ctx, resource); err != nil {
72 return fmt.Errorf("failed to refresh auxiliary token: %w", err)
73 }
74 }
75 return nil
76 }
77