diff --git a/eng/Directory.Build.Data.props b/eng/Directory.Build.Data.props
index 350f0c2993238..2dc8a3bb049c7 100644
--- a/eng/Directory.Build.Data.props
+++ b/eng/Directory.Build.Data.props
@@ -41,9 +41,10 @@
true
+ true
true
- true
- true
+ true
+ true
@@ -112,7 +113,7 @@
$(IntermediateOutputPath)$(TargetFramework)\$(MSBuildProjectName).xml
-
+
false
false
diff --git a/eng/Packages.Data.props b/eng/Packages.Data.props
index 28b3bffd87552..1825607ad303d 100755
--- a/eng/Packages.Data.props
+++ b/eng/Packages.Data.props
@@ -36,14 +36,10 @@
-
-
+
+
-
-
-
-
@@ -104,6 +100,10 @@
+
+
+
+
diff --git a/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/AppConfigurationAzureClientBuilderExtensions.cs b/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/AppConfigurationAzureClientBuilderExtensions.cs
deleted file mode 100644
index e9574825b4a78..0000000000000
--- a/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/AppConfigurationAzureClientBuilderExtensions.cs
+++ /dev/null
@@ -1,31 +0,0 @@
-// Copyright (c) Microsoft Corporation. All rights reserved.
-// Licensed under the MIT License.
-
-using System;
-using Azure.Core;
-
-namespace Azure.ApplicationModel.Configuration
-{
- ///
- /// App Configuration client builder
- ///
- public static class AppConfigurationAzureClientBuilderExtensions
- {
- public static TBuilder AddAppConfiguration(this TBuilder builder,
- string name,
- string connectionString,
- Action configureOptions = null)
- where TBuilder: IAzureClientsBuilder
- {
- builder.RegisterClient(name, options => new ConfigurationClient(connectionString, options), configureOptions);
- return builder;
- }
-
- public static TBuilder AddAppConfiguration(this TBuilder builder, string name, TConfiguration configuration)
- where TBuilder: IAzureClientsBuilderWithConfiguration
- {
- builder.RegisterClient(name, configuration);
- return builder;
- }
- }
-}
diff --git a/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/Azure.ApplicationModel.Configuration.csproj b/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/Azure.ApplicationModel.Configuration.csproj
index fd2276c6a487c..92019df4b546f 100644
--- a/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/Azure.ApplicationModel.Configuration.csproj
+++ b/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/Azure.ApplicationModel.Configuration.csproj
@@ -13,9 +13,6 @@
$(RequiredTargetFrameworks)
$(NoWarn);3021
true
-
-
- $(NoWarn);1591
diff --git a/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/AzureClientBuilderExtensions.cs b/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/AzureClientBuilderExtensions.cs
new file mode 100644
index 0000000000000..f4e147a6d9630
--- /dev/null
+++ b/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/AzureClientBuilderExtensions.cs
@@ -0,0 +1,31 @@
+// Copyright (c) Microsoft Corporation. All rights reserved.
+// Licensed under the MIT License.
+
+using Azure.Core.Extensions;
+
+namespace Azure.ApplicationModel.Configuration
+{
+ ///
+ /// Extension methods to add client to clients builder
+ ///
+ public static class AzureClientBuilderExtensions
+ {
+ ///
+ /// Registers a instance with the provided
+ ///
+ public static IAzureClientBuilder AddConfigurationClient(this TBuilder builder, string connectionString)
+ where TBuilder: IAzureClientFactoryBuilder
+ {
+ return builder.RegisterClientFactory(options => new ConfigurationClient(connectionString, options));
+ }
+
+ ///
+ /// Registers a instance with connection options loaded from the provided instance.
+ ///
+ public static IAzureClientBuilder AddConfigurationClient(this TBuilder builder, TConfiguration configuration)
+ where TBuilder: IAzureClientFactoryBuilderWithConfiguration
+ {
+ return builder.RegisterClientFactory(configuration);
+ }
+ }
+}
diff --git a/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/ConfigurationClientOptions.cs b/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/ConfigurationClientOptions.cs
index 8b9b4bb75c7f1..6f8f6de9849f0 100644
--- a/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/ConfigurationClientOptions.cs
+++ b/sdk/appconfiguration/Azure.ApplicationModel.Configuration/src/ConfigurationClientOptions.cs
@@ -20,6 +20,9 @@ public class ConfigurationClientOptions: ClientOptions
///
public enum ServiceVersion
{
+ ///
+ /// Uses the latest service version
+ ///
Default = 0
}
@@ -35,7 +38,7 @@ public enum ServiceVersion
///
///
/// The of the service API used when
- /// making requests.
+ /// making requests.
///
public ConfigurationClientOptions(ServiceVersion version = ServiceVersion.Default)
{
diff --git a/sdk/core/Azure.Core.Extensions/samples/Azure.Core.Extensions.Samples.csproj b/sdk/core/Azure.Core.Extensions/samples/Azure.Core.Extensions.Samples.csproj
new file mode 100644
index 0000000000000..9cc1af65dbc5c
--- /dev/null
+++ b/sdk/core/Azure.Core.Extensions/samples/Azure.Core.Extensions.Samples.csproj
@@ -0,0 +1,12 @@
+
+
+ netcoreapp2.1
+ $(RequiredTargetFrameworks)
+ false
+
+
+
+
+
+
+
diff --git a/sdk/core/Azure.Core.Extensions/samples/CustomPolicy.cs b/sdk/core/Azure.Core.Extensions/samples/CustomPolicy.cs
new file mode 100644
index 0000000000000..68bfaa8617a46
--- /dev/null
+++ b/sdk/core/Azure.Core.Extensions/samples/CustomPolicy.cs
@@ -0,0 +1,24 @@
+// Copyright (c) Microsoft Corporation. All rights reserved.
+// Licensed under the MIT License.
+
+using Azure.Core.Pipeline;
+using Microsoft.AspNetCore.Hosting;
+
+namespace Azure.Core.Extensions.Samples
+{
+ internal class DependencyInjectionEnabledPolicy : SynchronousHttpPipelinePolicy
+ {
+ private readonly IHostingEnvironment _environment;
+
+ public DependencyInjectionEnabledPolicy(IHostingEnvironment environment)
+ {
+ this._environment = environment;
+ }
+
+ public override void OnSendingRequest(HttpPipelineMessage message)
+ {
+ message.Request.Headers.Add("application-name", _environment.ApplicationName);
+ base.OnSendingRequest(message);
+ }
+ }
+}
\ No newline at end of file
diff --git a/sdk/core/Azure.Core.Extensions/samples/Program.cs b/sdk/core/Azure.Core.Extensions/samples/Program.cs
new file mode 100644
index 0000000000000..8ad09e68bc66a
--- /dev/null
+++ b/sdk/core/Azure.Core.Extensions/samples/Program.cs
@@ -0,0 +1,20 @@
+// Copyright (c) Microsoft Corporation. All rights reserved.
+// Licensed under the MIT License.
+
+using Microsoft.AspNetCore;
+using Microsoft.AspNetCore.Hosting;
+
+namespace Azure.Core.Extensions.Samples
+{
+ public class Program
+ {
+ public static void Main(string[] args)
+ {
+ CreateHostBuilder(args).Build().Run();
+ }
+
+ public static IWebHostBuilder CreateHostBuilder(string[] args) =>
+ WebHost.CreateDefaultBuilder(args)
+ .UseStartup();
+ }
+}
diff --git a/sdk/core/Azure.Core.Extensions/samples/Startup.cs b/sdk/core/Azure.Core.Extensions/samples/Startup.cs
new file mode 100644
index 0000000000000..48089fdb38dc6
--- /dev/null
+++ b/sdk/core/Azure.Core.Extensions/samples/Startup.cs
@@ -0,0 +1,71 @@
+// Copyright (c) Microsoft Corporation. All rights reserved.
+// Licensed under the MIT License.
+
+using System;
+using Azure.Core.Pipeline;
+using Azure.Identity;
+using Azure.Security.KeyVault.Secrets;
+using Microsoft.AspNetCore.Builder;
+using Microsoft.AspNetCore.Hosting;
+using Microsoft.AspNetCore.Http;
+using Microsoft.Extensions.Configuration;
+using Microsoft.Extensions.DependencyInjection;
+
+namespace Azure.Core.Extensions.Samples
+{
+ public class Startup
+ {
+ public IConfiguration Configuration { get; }
+
+ public Startup(IConfiguration configuration)
+ {
+ Configuration = configuration;
+ }
+
+ // This method gets called by the runtime. Use this method to add services to the container.
+ // For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=398940
+ public void ConfigureServices(IServiceCollection services)
+ {
+ // Registering policy to use in ConfigureDefaults later
+ services.AddSingleton();
+
+ services.AddAzureClients(builder => {
+
+ builder.AddSecretClient(Configuration.GetSection("KeyVault"))
+ .WithName("Default")
+ .WithCredential(new DefaultAzureCredential())
+ .ConfigureOptions(options => options.Retry.MaxRetries = 10);
+
+ builder.AddSecretClient(new Uri("http://my.keyvault.com"));
+
+ builder.UseCredential(new DefaultAzureCredential());
+
+ // This would use configuration for auth and client settings
+ builder.ConfigureDefaults(Configuration.GetSection("Default"));
+
+ // Configure global defaults
+ builder.ConfigureDefaults(options => options.Retry.Mode = RetryMode.Exponential);
+
+ // Advanced configure global defaults
+ builder.ConfigureDefaults((options, provider) => options.AddPolicy(HttpPipelinePosition.PerCall, provider.GetService()));
+ });
+ }
+
+ // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
+ public void Configure(IApplicationBuilder app, IHostingEnvironment env, SecretClient secretClient)
+ {
+ if (env.IsDevelopment())
+ {
+ app.UseDeveloperExceptionPage();
+ }
+
+ app.Run(async context => {
+ context.Response.ContentType = "text";
+ foreach (var secret in secretClient.GetSecrets())
+ {
+ await context.Response.WriteAsync(secret.Value.Name + Environment.NewLine);
+ }
+ });
+ }
+ }
+}
diff --git a/sdk/core/Azure.Core.Extensions/samples/appsettings.json b/sdk/core/Azure.Core.Extensions/samples/appsettings.json
new file mode 100644
index 0000000000000..10d2bfca313c7
--- /dev/null
+++ b/sdk/core/Azure.Core.Extensions/samples/appsettings.json
@@ -0,0 +1,20 @@
+{
+ "Logging": {
+ "LogLevel": {
+ "Default": "Debug"
+ }
+ },
+ "AllowedHosts": "*",
+ "Default": {
+ "ClientId": "",
+ "ClientSecret": "",
+ "TenantId": "",
+
+ "TelemetryPolicy": {
+ "ApplicationId": "AppId"
+ }
+ },
+ "KeyVault": {
+ "VaultUri": ""
+ }
+}
diff --git a/sdk/core/Azure.Core.Extensions/src/Azure.Core.Extensions.csproj b/sdk/core/Azure.Core.Extensions/src/Azure.Core.Extensions.csproj
index b04fa080696c2..0c26e74acae89 100644
--- a/sdk/core/Azure.Core.Extensions/src/Azure.Core.Extensions.csproj
+++ b/sdk/core/Azure.Core.Extensions/src/Azure.Core.Extensions.csproj
@@ -30,6 +30,7 @@
+
diff --git a/sdk/core/Azure.Core.Extensions/src/AzureClientBuilderExtensions.cs b/sdk/core/Azure.Core.Extensions/src/AzureClientBuilderExtensions.cs
new file mode 100644
index 0000000000000..f50e870d0aa8b
--- /dev/null
+++ b/sdk/core/Azure.Core.Extensions/src/AzureClientBuilderExtensions.cs
@@ -0,0 +1,53 @@
+// Copyright (c) Microsoft Corporation. All rights reserved.
+// Licensed under the MIT License.
+
+using System;
+using Microsoft.Extensions.Configuration;
+using Microsoft.Extensions.DependencyInjection;
+using Microsoft.Extensions.Options;
+
+namespace Azure.Core.Extensions
+{
+ public static class AzureClientBuilderExtensions
+ {
+ public static IAzureClientBuilder WithName(this IAzureClientBuilder builder, string name) where TOptions : class
+ {
+ builder.ToBuilder().Registration.Name = name;
+ return builder;
+ }
+
+ public static IAzureClientBuilder WithCredential(this IAzureClientBuilder builder, TokenCredential credential) where TOptions : class
+ {
+ return builder.WithCredential(_ => credential);
+ }
+
+ public static IAzureClientBuilder WithCredential(this IAzureClientBuilder builder, Func credentialFactory) where TOptions : class
+ {
+ var impl = builder.ToBuilder();
+ impl.ServiceCollection.AddSingleton>>(new ConfigureClientCredentials(impl.Registration, credentialFactory));
+ return builder;
+ }
+
+ public static IAzureClientBuilder ConfigureOptions(this IAzureClientBuilder builder, Action configureOptions) where TOptions : class
+ {
+ return builder.ConfigureOptions((options, _) => configureOptions(options));
+ }
+
+ public static IAzureClientBuilder ConfigureOptions(this IAzureClientBuilder builder, IConfiguration configuration) where TOptions : class
+ {
+ return builder.ConfigureOptions(options => configuration.Bind(options));
+ }
+
+ public static IAzureClientBuilder ConfigureOptions(this IAzureClientBuilder builder, Action configureOptions) where TOptions : class
+ {
+ var impl = builder.ToBuilder();
+ impl.ServiceCollection.AddSingleton>(provider => new ConfigureClientOptions(provider, impl.Registration, configureOptions));;
+ return builder;
+ }
+
+ private static AzureClientBuilder ToBuilder(this IAzureClientBuilder builder) where TOptions : class
+ {
+ return (AzureClientBuilder)builder;
+ }
+ }
+}
\ No newline at end of file
diff --git a/sdk/core/Azure.Core.Extensions/src/AzureClientFactoryBuilder.cs b/sdk/core/Azure.Core.Extensions/src/AzureClientFactoryBuilder.cs
new file mode 100644
index 0000000000000..e9c98a17c5a8b
--- /dev/null
+++ b/sdk/core/Azure.Core.Extensions/src/AzureClientFactoryBuilder.cs
@@ -0,0 +1,93 @@
+// Copyright (c) Microsoft Corporation. All rights reserved.
+// Licensed under the MIT License.
+
+using System;
+using Azure.Core.Pipeline;
+using Microsoft.Extensions.Configuration;
+using Microsoft.Extensions.DependencyInjection;
+using Microsoft.Extensions.DependencyInjection.Extensions;
+using Microsoft.Extensions.Options;
+
+namespace Azure.Core.Extensions
+{
+ public sealed class AzureClientFactoryBuilder : IAzureClientFactoryBuilderWithConfiguration, IAzureClientsBuilderWithCredential
+ {
+ private readonly IServiceCollection _serviceCollection;
+
+ internal const string DefaultClientName = "Default";
+
+ internal AzureClientFactoryBuilder(IServiceCollection serviceCollection)
+ {
+ _serviceCollection = serviceCollection;
+ _serviceCollection.AddOptions();
+ _serviceCollection.TryAddSingleton();
+ }
+
+ IAzureClientBuilder IAzureClientFactoryBuilder.RegisterClientFactory(Func clientFactory)
+ {
+ return ((IAzureClientsBuilderWithCredential)this).RegisterClientFactory((options, _) => clientFactory(options));
+ }
+
+ IAzureClientBuilder IAzureClientFactoryBuilderWithConfiguration.RegisterClientFactory(IConfiguration configuration)
+ {
+ return ((IAzureClientsBuilderWithCredential)this).RegisterClientFactory(
+ (options, credentials) => (TClient)ClientFactory.CreateClient(typeof(TClient), typeof(TOptions), options, configuration, credentials))
+ .ConfigureOptions(configuration)
+ .WithCredential(ClientFactory.CreateCredential(configuration));
+ }
+
+ public AzureClientFactoryBuilder ConfigureDefaults(Action configureOptions)
+ {
+ ConfigureDefaults((options, provider) => configureOptions(options));
+ return this;
+ }
+
+ public AzureClientFactoryBuilder ConfigureDefaults(Action configureOptions)
+ {
+ _serviceCollection.Configure(options => options.ConfigureOptionDelegates.Add(configureOptions));
+
+ return this;
+ }
+
+ public AzureClientFactoryBuilder ConfigureDefaults(IConfiguration configuration)
+ {
+ ConfigureDefaults(options => configuration.Bind(options));
+
+ var credentialsFromConfig = ClientFactory.CreateCredential(configuration);
+
+ if (credentialsFromConfig != null)
+ {
+ UseCredential(credentialsFromConfig);
+ }
+
+ return this;
+ }
+
+ IAzureClientBuilder IAzureClientsBuilderWithCredential.RegisterClientFactory(Func clientFactory)
+ {
+ var clientRegistration = new ClientRegistration(DefaultClientName, clientFactory);
+ _serviceCollection.AddSingleton(clientRegistration);
+
+ _serviceCollection.TryAddSingleton(typeof(IConfigureOptions>), typeof(DefaultCredentialClientOptionsSetup));
+ _serviceCollection.TryAddSingleton(typeof(IConfigureOptions), typeof(DefaultClientOptionsSetup));
+ _serviceCollection.TryAddSingleton(typeof(IAzureClientFactory), typeof(AzureClientFactory));
+ _serviceCollection.TryAddSingleton(
+ typeof(TClient),
+ provider => provider.GetService>().CreateClient(DefaultClientName));
+
+ return new AzureClientBuilder(clientRegistration, _serviceCollection);
+ }
+
+
+ public AzureClientFactoryBuilder UseCredential(TokenCredential tokenCredential)
+ {
+ return UseCredential(_ => tokenCredential);
+ }
+
+ public AzureClientFactoryBuilder UseCredential(Func tokenCredentialFactory)
+ {
+ _serviceCollection.Configure(options => options.CredentialFactory = tokenCredentialFactory);
+ return this;
+ }
+ }
+}
\ No newline at end of file
diff --git a/sdk/core/Azure.Core.Extensions/src/AzureClientsBuilder.cs b/sdk/core/Azure.Core.Extensions/src/AzureClientsBuilder.cs
deleted file mode 100644
index 862c9f8bfba33..0000000000000
--- a/sdk/core/Azure.Core.Extensions/src/AzureClientsBuilder.cs
+++ /dev/null
@@ -1,42 +0,0 @@
-// Copyright (c) Microsoft Corporation. All rights reserved.
-// Licensed under the MIT License.
-
-using System;
-using Microsoft.Extensions.Configuration;
-using Microsoft.Extensions.DependencyInjection;
-using Microsoft.Extensions.DependencyInjection.Extensions;
-
-namespace Azure.Core.Extensions
-{
- public sealed class AzureClientsBuilder : IAzureClientsBuilderWithConfiguration
- {
- private readonly IServiceCollection _serviceCollection;
-
- internal AzureClientsBuilder(IServiceCollection serviceCollection)
- {
- _serviceCollection = serviceCollection;
- _serviceCollection.AddOptions();
- _serviceCollection.TryAddSingleton();
- }
-
- void IAzureClientsBuilder.RegisterClient(string name, Func clientFactory, Action configureOptions)
- {
- _serviceCollection.AddSingleton(new ClientRegistration(name, clientFactory));
-
- _serviceCollection.TryAddSingleton(typeof(IAzureClientFactory), typeof(AzureClientFactory));
-
- if (configureOptions != null)
- {
- _serviceCollection.Configure(name, configureOptions);
- }
- }
-
- void IAzureClientsBuilderWithConfiguration.RegisterClient(string name, IConfiguration configuration)
- {
- ((IAzureClientsBuilder)this).RegisterClient(
- name,
- options => (TClient)ConfigurationClientFactory.CreateClient(typeof(TClient), typeof(TOptions), options, configuration),
- options => configuration.Bind(options));
- }
- }
-}
\ No newline at end of file
diff --git a/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientBuilder.cs b/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientBuilder.cs
new file mode 100644
index 0000000000000..0608d8c7dbabf
--- /dev/null
+++ b/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientBuilder.cs
@@ -0,0 +1,19 @@
+// Copyright (c) Microsoft Corporation. All rights reserved.
+// Licensed under the MIT License.
+
+using Microsoft.Extensions.DependencyInjection;
+
+namespace Azure.Core.Extensions
+{
+ internal sealed class AzureClientBuilder: IAzureClientBuilder where TOptions : class
+ {
+ public ClientRegistration Registration { get; }
+ public IServiceCollection ServiceCollection { get; }
+
+ internal AzureClientBuilder(ClientRegistration clientRegistration, IServiceCollection serviceCollection)
+ {
+ Registration = clientRegistration;
+ ServiceCollection = serviceCollection;
+ }
+ }
+}
\ No newline at end of file
diff --git a/sdk/core/Azure.Core.Extensions/src/AzureClientFactory.cs b/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientFactory.cs
similarity index 64%
rename from sdk/core/Azure.Core.Extensions/src/AzureClientFactory.cs
rename to sdk/core/Azure.Core.Extensions/src/Internal/AzureClientFactory.cs
index 7518dd431396c..63ae6845a34d9 100644
--- a/sdk/core/Azure.Core.Extensions/src/AzureClientFactory.cs
+++ b/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientFactory.cs
@@ -3,7 +3,6 @@
using System;
using System.Collections.Generic;
-using System.Linq;
using Microsoft.Extensions.Options;
namespace Azure.Core.Extensions
@@ -12,11 +11,19 @@ internal class AzureClientFactory: IAzureClientFactory> _clientRegistrations;
+ private readonly IServiceProvider _serviceProvider;
+
+ private readonly IOptionsMonitor> _clientsOptions;
+
private readonly IOptionsMonitor _monitor;
private readonly EventSourceLogForwarder _logForwarder;
- public AzureClientFactory(IEnumerable> clientRegistrations, IOptionsMonitor monitor, EventSourceLogForwarder logForwarder)
+ public AzureClientFactory(
+ IServiceProvider serviceProvider,
+ IOptionsMonitor> clientsOptions,
+ IEnumerable> clientRegistrations, IOptionsMonitor monitor,
+ EventSourceLogForwarder logForwarder)
{
_clientRegistrations = new Dictionary>();
foreach (var registration in clientRegistrations)
@@ -24,6 +31,8 @@ public AzureClientFactory(IEnumerable> cli
_clientRegistrations[registration.Name] = registration;
}
+ _serviceProvider = serviceProvider;
+ _clientsOptions = clientsOptions;
_monitor = monitor;
_logForwarder = logForwarder;
}
@@ -35,7 +44,7 @@ public TClient CreateClient(string name)
throw new InvalidOperationException($"Unable to find client registration with type '{typeof(TClient).Name}' and name '{name}'.");
}
- return registration.GetClient(_monitor.Get(name));
+ return registration.GetClient(_monitor.Get(name), _clientsOptions.Get(name).CredentialFactory(_serviceProvider));
}
}
}
\ No newline at end of file
diff --git a/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientOptions.cs b/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientOptions.cs
new file mode 100644
index 0000000000000..e844e5a81ac9e
--- /dev/null
+++ b/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientOptions.cs
@@ -0,0 +1,12 @@
+// Copyright (c) Microsoft Corporation. All rights reserved.
+// Licensed under the MIT License.
+
+using System;
+
+namespace Azure.Core.Extensions
+{
+ internal class AzureClientCredentialOptions
+ {
+ public Func CredentialFactory { get; set; }
+ }
+}
\ No newline at end of file
diff --git a/sdk/core/Azure.Core.Extensions/src/AzureClientServiceCollectionExtensions.cs b/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientServiceCollectionExtensions.cs
similarity index 71%
rename from sdk/core/Azure.Core.Extensions/src/AzureClientServiceCollectionExtensions.cs
rename to sdk/core/Azure.Core.Extensions/src/Internal/AzureClientServiceCollectionExtensions.cs
index afb7ea165a2aa..26c9ccef16e0c 100644
--- a/sdk/core/Azure.Core.Extensions/src/AzureClientServiceCollectionExtensions.cs
+++ b/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientServiceCollectionExtensions.cs
@@ -8,9 +8,9 @@ namespace Azure.Core.Extensions
{
public static class AzureClientServiceCollectionExtensions
{
- public static void AddAzureClients(this IServiceCollection collection, Action configureClients)
+ public static void AddAzureClients(this IServiceCollection collection, Action configureClients)
{
- configureClients(new AzureClientsBuilder(collection));
+ configureClients(new AzureClientFactoryBuilder(collection));
}
}
}
\ No newline at end of file
diff --git a/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientsGlobalOptions.cs b/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientsGlobalOptions.cs
new file mode 100644
index 0000000000000..cf21a19ee8144
--- /dev/null
+++ b/sdk/core/Azure.Core.Extensions/src/Internal/AzureClientsGlobalOptions.cs
@@ -0,0 +1,16 @@
+// Copyright (c) Microsoft Corporation. All rights reserved.
+// Licensed under the MIT License.
+
+using System;
+using System.Collections.Generic;
+using Azure.Core.Pipeline;
+using Azure.Identity;
+
+namespace Azure.Core.Extensions
+{
+ internal class AzureClientsGlobalOptions
+ {
+ public Func CredentialFactory { get; set; } = _ => new DefaultAzureCredential();
+ public List> ConfigureOptionDelegates { get; } = new List>();
+ }
+}
\ No newline at end of file
diff --git a/sdk/core/Azure.Core.Extensions/src/ClientInformation.cs b/sdk/core/Azure.Core.Extensions/src/Internal/ClientInformation.cs
similarity index 75%
rename from sdk/core/Azure.Core.Extensions/src/ClientInformation.cs
rename to sdk/core/Azure.Core.Extensions/src/Internal/ClientInformation.cs
index f086e78d327bc..e898c737d6ef7 100644
--- a/sdk/core/Azure.Core.Extensions/src/ClientInformation.cs
+++ b/sdk/core/Azure.Core.Extensions/src/Internal/ClientInformation.cs
@@ -8,9 +8,9 @@ namespace Azure.Core.Extensions
{
internal class ClientRegistration
{
- public string Name { get; }
+ public string Name { get; set; }
- private readonly Func _factory;
+ private readonly Func _factory;
private readonly object _cacheLock = new object();
@@ -18,13 +18,13 @@ internal class ClientRegistration
private ExceptionDispatchInfo _cachedException;
- public ClientRegistration(string name, Func factory)
+ public ClientRegistration(string name, Func factory)
{
Name = name;
_factory = factory;
}
- public TClient GetClient(TOptions options)
+ public TClient GetClient(TOptions options, TokenCredential tokenCredential)
{
_cachedException?.Throw();
@@ -44,7 +44,7 @@ public TClient GetClient(TOptions options)
try
{
- _cachedClient = _factory(options);
+ _cachedClient = _factory(options, tokenCredential);
}
catch (Exception e)
{
diff --git a/sdk/core/Azure.Core.Extensions/src/ConfigurationClientFactory.cs b/sdk/core/Azure.Core.Extensions/src/Internal/ConfigurationClientFactory.cs
similarity index 58%
rename from sdk/core/Azure.Core.Extensions/src/ConfigurationClientFactory.cs
rename to sdk/core/Azure.Core.Extensions/src/Internal/ConfigurationClientFactory.cs
index f648877698c78..0c25bdf673b93 100644
--- a/sdk/core/Azure.Core.Extensions/src/ConfigurationClientFactory.cs
+++ b/sdk/core/Azure.Core.Extensions/src/Internal/ConfigurationClientFactory.cs
@@ -4,14 +4,16 @@
using System;
using System.Collections.Generic;
using System.Reflection;
+using System.Security.Cryptography.X509Certificates;
using System.Text;
+using Azure.Identity;
using Microsoft.Extensions.Configuration;
namespace Azure.Core.Extensions
{
- internal class ConfigurationClientFactory
+ internal class ClientFactory
{
- public static object CreateClient(Type clientType, Type optionsType, object options, IConfiguration configuration)
+ public static object CreateClient(Type clientType, Type optionsType, object options, IConfiguration configuration, TokenCredential credential)
{
List