/// <summary> /// Initialize a CredHub Client with user credentials for the appropriate UAA server /// </summary> /// <param name="credHubOptions">CredHub client configuration values</param> /// <param name="logger">Pass in a logger if you want logs</param> /// <param name="httpClient">Primarily for tests, optionally provide your own http client</param> /// <returns>An initialized CredHub client (using UAA OAuth)</returns> public static Task<CredHubClient> CreateUAAClientAsync(CredHubOptions credHubOptions, ILogger logger = null, HttpClient httpClient = null) { _logger = logger; _baseCredHubUrl = credHubOptions.CredHubUrl; var client = new CredHubClient(credHubOptions.ValidateCertificates); _httpClientHandler = new HttpClientHandler(); _httpClient = httpClient ?? client.InitializeHttpClient(_httpClientHandler); return client.InitializeAsync(credHubOptions); }
private async Task <CredHubClient> InitializeAsync(CredHubOptions options) { HttpClientHelper.ConfigureCertificateValidation(_validateCertificates, out SecurityProtocolType protocolType, out RemoteCertificateValidationCallback prevValidator); try { Uri tokenUri; var uaaOverrideUrl = Environment.GetEnvironmentVariable("UAA_Server_Override"); if (string.IsNullOrEmpty(uaaOverrideUrl)) { var info = await _httpClient.GetAsync($"{_baseCredHubUrl.Replace("/api", "/info")}").ConfigureAwait(false); var infoResponse = await HandleErrorParseResponse <CredHubServerInfo>(info, "GET /info from CredHub Server").ConfigureAwait(false); tokenUri = new Uri($"{infoResponse.AuthServer.First().Value}/oauth/token"); _logger?.LogInformation($"Targeted CredHub server uses UAA server at {tokenUri}"); } else { tokenUri = new Uri(uaaOverrideUrl); _logger?.LogInformation($"UAA set by ENV variable {tokenUri}"); } // login to UAA var header = new AuthenticationHeaderValue("Basic", Convert.ToBase64String(Encoding.ASCII.GetBytes($"{options.ClientId}:{options.ClientSecret}"))); _httpClient.DefaultRequestHeaders.Authorization = header; var postParams = new List <KeyValuePair <string, string> > { new KeyValuePair <string, string>("grant_type", "client_credentials"), new KeyValuePair <string, string>("response_type", "token") }; var response = await _httpClient.PostAsync(tokenUri, new FormUrlEncodedContent(postParams)).ConfigureAwait(false); if (response.IsSuccessStatusCode) { _logger?.LogTrace(await response.Content.ReadAsStringAsync().ConfigureAwait(false)); // set the token var payload = JObject.Parse(await response.Content.ReadAsStringAsync().ConfigureAwait(false)); _httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", payload.Value <string>("access_token")); return(this); } else { _logger?.LogCritical($"Authentication with UAA Server failed, status code: {response.StatusCode}"); _logger?.LogCritical(await response.Content.ReadAsStringAsync().ConfigureAwait(false)); throw new AuthenticationException($"Authentication with UAA Server failed, status code: {response.StatusCode}"); } } finally { HttpClientHelper.RestoreCertificateValidation(_validateCertificates, protocolType, prevValidator); } }
private async Task <CredHubClient> InitializeAsync(CredHubOptions options) { HttpClientHelper.ConfigureCertificateValidation(_validateCertificates, out var protocolType, out var prevValidator); try { Uri tokenUri; var uaaOverrideUrl = Environment.GetEnvironmentVariable("UAA_Server_Override"); if (string.IsNullOrEmpty(uaaOverrideUrl)) { var info = await _httpClient.GetAsync($"{_baseCredHubUrl.Replace("/api", "/info")}").ConfigureAwait(false); var infoResponse = await HandleErrorParseResponse <CredHubServerInfo>(info, "GET /info from CredHub Server").ConfigureAwait(false); tokenUri = new Uri($"{infoResponse.AuthServer.First().Value}/oauth/token"); _logger?.LogInformation($"Targeted CredHub server uses UAA server at {tokenUri}"); } else { tokenUri = new Uri(uaaOverrideUrl); _logger?.LogInformation($"UAA set by ENV variable {tokenUri}"); } // login to UAA var token = await HttpClientHelper.GetAccessToken( tokenUri, options.ClientId, options.ClientSecret, additionalParams : new Dictionary <string, string> { { "response_type", "token" } }, httpClient : _httpClient, logger : _logger); if (token is object) { // set the token _httpClient.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", token); return(this); } else { throw new AuthenticationException($"Authentication with UAA Server failed"); } } finally { HttpClientHelper.RestoreCertificateValidation(_validateCertificates, protocolType, prevValidator); } }
/// <summary> /// Expects CF_INSTANCE_CERT and CF_INSTANCE_KEY to be set in the environment (automatically set by DIEGO in cloud foundry) /// </summary> /// <param name="credHubOptions">CredHub client configuration values</param> /// <param name="logger">Pass in a logger if you want logs</param> /// <param name="httpClient">Optionally override the http client used to talk to credhub - added for tests only</param> /// <returns>An initialized CredHub client (using mTLS)</returns> public static async Task <CredHubClient> CreateMTLSClientAsync(CredHubOptions credHubOptions, ILogger logger = null, HttpClient httpClient = null) { _logger = logger; _baseCredHubUrl = credHubOptions.CredHubUrl; var cfInstanceCert = Environment.GetEnvironmentVariable("CF_INSTANCE_CERT") ?? string.Empty; var cfInstanceKey = Environment.GetEnvironmentVariable("CF_INSTANCE_KEY"); if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows) && cfInstanceCert.StartsWith("/")) { _logger?.LogTrace("Detected Windows OS and root-relative paths for application credentials: converting to app-relative paths"); cfInstanceCert = ".." + cfInstanceCert; cfInstanceKey = ".." + cfInstanceKey; } if (string.IsNullOrEmpty(cfInstanceCert) || string.IsNullOrEmpty(cfInstanceKey)) { _logger?.LogCritical("Cloud Foundry application credentials not found in the environment"); throw new ArgumentException("Application Credentials not found (Missing ENV variable for Instance Cert and/or Key)"); } _logger?.LogTrace("Application certificate: " + cfInstanceCert); _logger?.LogTrace("Application key: " + cfInstanceKey); if (File.Exists(cfInstanceCert) && File.Exists(cfInstanceKey)) { var client = new CredHubClient(credHubOptions.ValidateCertificates); _httpClientHandler = new HttpClientHandler() { ClientCertificateOptions = ClientCertificateOption.Manual }; var certBytes = File.ReadAllBytes(cfInstanceCert); var keyBytes = File.ReadAllBytes(cfInstanceKey); var appCredentials = CertificateHelpers.GetX509FromBytes(certBytes, keyBytes); if (!appCredentials.HasPrivateKey) { throw new Exception("Private key is missing, mTLS won't work"); } _httpClientHandler.ClientCertificates.Add(appCredentials); _httpClient = httpClient ?? client.InitializeHttpClient(_httpClientHandler); return(await client.InitializeAsync()); } else { throw new Exception($"Application credentials not found (Failed to load Instance Cert [{cfInstanceCert}] and/or Key [{cfInstanceKey}])"); } }