예제 #1
0
 public KeyVaultClient(HttpClient httpClient = null, NonInteractiveAzureServiceTokenProviderBase tokenProvider = null)
 {
     _httpClient    = httpClient ?? new HttpClient();
     _tokenProvider = tokenProvider;
 }
 /// <summary>
 /// This method is for testing only
 /// </summary>
 internal AzureServiceTokenProvider(NonInteractiveAzureServiceTokenProviderBase accessTokenProvider)
 {
     _selectedAccessTokenProvider = accessTokenProvider;
 }
예제 #3
0
        /// <summary>
        /// This is the core method to get a token. It checks if the token is in cache, and if so, returns it.
        /// If not in cache, asks one or more token providers to get the token.
        /// </summary>
        /// <param name="authority"></param>
        /// <param name="resource"></param>
        /// <param name="scope"></param>
        /// <returns></returns>
        private async Task <AppAuthenticationResult> GetAuthResultAsyncImpl(string resource, string authority,
                                                                            CancellationToken cancellationToken = default(CancellationToken))
        {
            // Check if the auth result is present in cache, for the given connection string, authority, and resource
            // This is an in-memory global cache, that will be used across instances of this class.
            string cacheKey = $"ConnectionString:{_connectionString};Authority:{authority};Resource:{resource}";

            Tuple <AppAuthenticationResult, Principal> cachedAuthResult = AppAuthResultCache.Get(cacheKey);

            if (cachedAuthResult != null)
            {
                _principalUsed = cachedAuthResult.Item2;

                return(cachedAuthResult.Item1);
            }

            // If not in cache, lock. One of multiple threads that reach here will be allowed to get the token.
            // When the first thread gets the token, another thread will be let in the lock.
            await Semaphore.WaitAsync().ConfigureAwait(false);

            // This is to store the list of exceptions while trying to get the token.
            List <Exception> exceptions = new List <Exception>();

            try
            {
                // Check again if the auth result is in the cache now, the first thread may have gotten it.
                cachedAuthResult = AppAuthResultCache.Get(cacheKey);

                if (cachedAuthResult != null)
                {
                    _principalUsed = cachedAuthResult.Item2;

                    return(cachedAuthResult.Item1);
                }

                // If the auth result was not in cache, try to get it
                List <NonInteractiveAzureServiceTokenProviderBase> tokenProviders = GetTokenProviders();

                // Try to get the token using the selected providers
                foreach (var tokenProvider in tokenProviders)
                {
                    try
                    {
                        // Get the auth result, add to the cache, and return the auth result.
                        var authResult = await tokenProvider.GetAuthResultAsync(resource, authority, cancellationToken)
                                         .ConfigureAwait(false);

                        // Set the token provider to the one that worked.
                        // Future calls to get token in this instance will directly use this provider.
                        _selectedAccessTokenProvider = tokenProvider;

                        _principalUsed = tokenProvider.PrincipalUsed;

                        AppAuthResultCache.AddOrUpdate(cacheKey,
                                                       new Tuple <AppAuthenticationResult, Principal>(authResult, tokenProvider.PrincipalUsed));

                        return(authResult);
                    }
                    catch (AzureServiceTokenProviderException exp)
                    {
                        exceptions.Add(exp);
                    }
                }
            }
            finally
            {
                // Whichever way the try block exits, the semaphore must be released.
                Semaphore.Release();
            }

            // Throw exception so that the caller knows why the token could not be acquired.
            if (exceptions.Count == 1)
            {
                throw exceptions.First();
            }

            string message = $"Tried the following {exceptions.Count} methods to get an access token, but none of them worked.{Environment.NewLine}";

            foreach (var exception in exceptions)
            {
                message += $"{exception.Message}{Environment.NewLine}";
            }

            throw new AzureServiceTokenProviderException(null, resource, authority, message);
        }
 internal KeyVaultClient(HttpClient httpClient, NonInteractiveAzureServiceTokenProviderBase tokenProvider = null) : this(0, httpClient, tokenProvider)
 {
 }
 internal KeyVaultClient(int msiRetryTimeoutInSeconds = 0, HttpClient httpClient = null, NonInteractiveAzureServiceTokenProviderBase tokenProvider = null)
 {
     _msiRetryTimeoutInSeconds = msiRetryTimeoutInSeconds;
     _httpClient    = httpClient ?? new HttpClient();
     _tokenProvider = tokenProvider;
 }
예제 #6
0
 internal KeyVaultClient(HttpClient httpClient, NonInteractiveAzureServiceTokenProviderBase tokenProvider = null, string managedIdentityClientId = null) : this(0, managedIdentityClientId, httpClient, tokenProvider)
 {
 }
예제 #7
0
        internal KeyVaultClient(int msiRetryTimeoutInSeconds = 0, string managedIdentityClientId = null, HttpClient httpClient = null, NonInteractiveAzureServiceTokenProviderBase tokenProvider = null)
        {
            _msiRetryTimeoutInSeconds = msiRetryTimeoutInSeconds;
#if NETSTANDARD1_4 || net452 || net461
            _httpClient = httpClient ?? new HttpClient();
#else
            _httpClient = httpClient ?? new HttpClient(new HttpClientHandler()
            {
                CheckCertificateRevocationList = true
            });
#endif
            _tokenProvider           = tokenProvider;
            _managedIdentityClientId = managedIdentityClientId;
        }