Use new generic host UseDefaultServiceProvider call (#5703)

This commit is contained in:
Chris Ross 2018-12-19 12:17:58 -08:00 committed by GitHub
parent e21fe567b2
commit 03867f08ab
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
15 changed files with 19 additions and 215 deletions

View File

@ -1,4 +1,4 @@
// Copyright (c) .NET Foundation. All rights reserved.
// Copyright (c) .NET Foundation. All rights reserved.
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
using System;
@ -196,16 +196,12 @@ namespace Microsoft.AspNetCore.Hosting.Internal
public IWebHostBuilder UseDefaultServiceProvider(Action<WebHostBuilderContext, ServiceProviderOptions> configure)
{
// REVIEW: This is a hack to change the builder with the HostBuilderContext in scope,
// we're not actually using configuration here
_builder.ConfigureAppConfiguration((context, _) =>
_builder.UseServiceProviderFactory(context =>
{
var webHostBuilderContext = GetWebHostBuilderContext(context);
var options = new ServiceProviderOptions();
configure(webHostBuilderContext, options);
// This is only fine because this runs last
_builder.UseServiceProviderFactory(new DefaultServiceProviderFactory(options));
return new DefaultServiceProviderFactory(options);
});
return this;
@ -373,4 +369,4 @@ namespace Microsoft.AspNetCore.Hosting.Internal
}
}
}
}
}

View File

@ -1,32 +0,0 @@
using System.Threading;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Hosting.Server;
using Microsoft.AspNetCore.Http.Features;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
namespace GenericWebHost
{
// We can't reference real servers in this sample without creating a circular repo dependency.
// This fake server lets us at least run the code.
public class FakeServer : IServer
{
public IFeatureCollection Features => new FeatureCollection();
public Task StartAsync<TContext>(IHttpApplication<TContext> application, CancellationToken cancellationToken) => Task.CompletedTask;
public Task StopAsync(CancellationToken cancellationToken) => Task.CompletedTask;
public void Dispose()
{
}
}
public static class FakeServerWebHostBuilderExtensions
{
public static IHostBuilder UseFakeServer(this IHostBuilder builder)
{
return builder.ConfigureServices((builderContext, services) => services.AddSingleton<IServer, FakeServer>());
}
}
}

View File

@ -9,10 +9,8 @@
<ItemGroup>
<Reference Include="Microsoft.AspNetCore.Hosting" />
<Reference Include="Microsoft.AspNetCore.Server.Kestrel" />
<Reference Include="Microsoft.Extensions.Hosting" />
<Reference Include="Microsoft.Extensions.Configuration.CommandLine" />
<Reference Include="Microsoft.Extensions.Configuration.EnvironmentVariables" />
<Reference Include="Microsoft.Extensions.Configuration.Json" />
</ItemGroup>
</Project>

View File

@ -1,4 +1,4 @@
using System.Threading.Tasks;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.Configuration;
@ -11,17 +11,11 @@ namespace GenericWebHost
{
public static async Task Main(string[] args)
{
var host = new HostBuilder()
.ConfigureAppConfiguration((hostContext, config) =>
{
config.AddEnvironmentVariables();
config.AddJsonFile("appsettings.json", optional: true);
config.AddCommandLine(args);
})
.UseFakeServer()
var host = Host.CreateDefaultBuilder()
.ConfigureWebHost(builder =>
{
builder.Configure(app =>
builder.UseKestrel()
.Configure(app =>
{
app.Run(async (context) =>
{
@ -29,7 +23,6 @@ namespace GenericWebHost
});
});
})
.UseConsoleLifetime()
.Build();
await host.RunAsync();

View File

@ -1,43 +0,0 @@
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Text;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Hosting.Internal;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.ObjectPool;
namespace GenericWebHost
{
public static class WebHostExtensions
{
public static IHostBuilder ConfigureWebHost(this IHostBuilder builder, Action<HostBuilderContext, IApplicationBuilder> configureApp)
{
return builder.ConfigureServices((bulderContext, services) =>
{
services.Configure<WebHostServiceOptions>(options =>
{
options.ConfigureApp = configureApp;
});
services.AddHostedService<WebHostService>();
var listener = new DiagnosticListener("Microsoft.AspNetCore");
services.AddSingleton<DiagnosticListener>(listener);
services.AddSingleton<DiagnosticSource>(listener);
services.AddTransient<IHttpContextFactory, HttpContextFactory>();
services.AddScoped<IMiddlewareFactory, MiddlewareFactory>();
// Conjure up a RequestServices
services.AddTransient<IStartupFilter, AutoRequestServicesStartupFilter>();
services.AddTransient<IServiceProviderFactory<IServiceCollection>, DefaultServiceProviderFactory>();
// Ensure object pooling is available everywhere.
services.AddSingleton<ObjectPoolProvider, DefaultObjectPoolProvider>();
});
}
}
}

View File

@ -1,62 +0,0 @@
using System;
using System.Diagnostics;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Builder.Internal;
using Microsoft.AspNetCore.Hosting.Internal;
using Microsoft.AspNetCore.Hosting.Server;
using Microsoft.AspNetCore.Hosting.Server.Features;
using Microsoft.AspNetCore.Http;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options;
namespace GenericWebHost
{
internal class WebHostService : IHostedService
{
public WebHostService(IOptions<WebHostServiceOptions> options, IServiceProvider services, HostBuilderContext hostBuilderContext, IServer server,
ILogger<WebHostService> logger, DiagnosticListener diagnosticListener, IHttpContextFactory httpContextFactory)
{
Options = options?.Value ?? throw new System.ArgumentNullException(nameof(options));
if (Options.ConfigureApp == null)
{
throw new ArgumentException(nameof(Options.ConfigureApp));
}
Services = services ?? throw new ArgumentNullException(nameof(services));
HostBuilderContext = hostBuilderContext ?? throw new ArgumentNullException(nameof(hostBuilderContext));
Server = server ?? throw new ArgumentNullException(nameof(server));
Logger = logger ?? throw new ArgumentNullException(nameof(logger));
DiagnosticListener = diagnosticListener ?? throw new ArgumentNullException(nameof(diagnosticListener));
HttpContextFactory = httpContextFactory ?? throw new ArgumentNullException(nameof(httpContextFactory));
}
public WebHostServiceOptions Options { get; }
public IServiceProvider Services { get; }
public HostBuilderContext HostBuilderContext { get; }
public IServer Server { get; }
public ILogger<WebHostService> Logger { get; }
public DiagnosticListener DiagnosticListener { get; }
public IHttpContextFactory HttpContextFactory { get; }
public Task StartAsync(CancellationToken cancellationToken)
{
Server.Features.Get<IServerAddressesFeature>()?.Addresses.Add("http://localhost:5000");
var builder = new ApplicationBuilder(Services, Server.Features);
Options.ConfigureApp(HostBuilderContext, builder);
var app = builder.Build();
var httpApp = new HostingApplication(app, Logger, DiagnosticListener, HttpContextFactory);
return Server.StartAsync(httpApp, cancellationToken);
}
public Task StopAsync(CancellationToken cancellationToken)
{
return Server.StopAsync(cancellationToken);
}
}
}

View File

@ -1,11 +0,0 @@
using System;
using Microsoft.AspNetCore.Builder;
using Microsoft.Extensions.Hosting;
namespace GenericWebHost
{
public class WebHostServiceOptions
{
public Action<HostBuilderContext, IApplicationBuilder> ConfigureApp { get; internal set; }
}
}

View File

@ -1,32 +0,0 @@
using System.Threading;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Hosting.Server;
using Microsoft.AspNetCore.Http.Features;
using Microsoft.Extensions.DependencyInjection;
namespace SampleStartups
{
// We can't reference real servers in this sample without creating a circular repo dependency.
// This fake server lets us at least run the code.
public class FakeServer : IServer
{
public IFeatureCollection Features => new FeatureCollection();
public Task StartAsync<TContext>(IHttpApplication<TContext> application, CancellationToken cancellationToken) => Task.CompletedTask;
public Task StopAsync(CancellationToken cancellationToken) => Task.CompletedTask;
public void Dispose()
{
}
}
public static class FakeServerWebHostBuilderExtensions
{
public static IWebHostBuilder UseFakeServer(this IWebHostBuilder builder)
{
return builder.ConfigureServices(services => services.AddSingleton<IServer, FakeServer>());
}
}
}

View File

@ -1,13 +1,14 @@
<Project Sdk="Microsoft.NET.Sdk">
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<TargetFramework>netcoreapp3.0</TargetFramework>
<StartupObject>SampleStartups.StartupInjection</StartupObject>
<StartupObject>SampleStartups.StartupBlockingOnStart</StartupObject>
<OutputType>exe</OutputType>
</PropertyGroup>
<ItemGroup>
<Reference Include="Microsoft.AspNetCore.Hosting" />
<Reference Include="Microsoft.AspNetCore.Server.Kestrel" />
<Reference Include="Microsoft.Extensions.Configuration.CommandLine" />
<Reference Include="Microsoft.Extensions.Configuration.EnvironmentVariables" />
<Reference Include="Microsoft.Extensions.Configuration.Json" />

View File

@ -33,7 +33,7 @@ namespace SampleStartups
var host = new WebHostBuilder()
.UseConfiguration(config)
.UseFakeServer()
.UseKestrel()
.UseStartup<StartupBlockingOnStart>()
.Build();

View File

@ -25,7 +25,7 @@ namespace SampleStartups
var host = new WebHostBuilder()
.UseConfiguration(config)
.UseFakeServer()
.UseKestrel()
.UseStartup<StartupConfigureAddresses>()
.UseUrls("http://localhost:5000", "http://localhost:5001")
.Build();

View File

@ -30,8 +30,7 @@ namespace SampleStartups
public void Start()
{
_host = new WebHostBuilder()
//.UseKestrel()
.UseFakeServer()
.UseKestrel()
.UseStartup<StartupExternallyControlled>()
.Start(_urls.ToArray());
}

View File

@ -22,8 +22,7 @@ namespace SampleStartups
var host = new WebHostBuilder()
.UseConfiguration(config) // Default set of configurations to use, may be subsequently overridden
//.UseKestrel()
.UseFakeServer()
.UseKestrel()
.UseContentRoot(Directory.GetCurrentDirectory()) // Override the content root with the current directory
.UseUrls("http://*:1000", "https://*:902")
.UseEnvironment(EnvironmentName.Development)

View File

@ -21,8 +21,7 @@ namespace SampleStartups
public static void Main(string[] args)
{
var host = new WebHostBuilder()
//.UseKestrel()
.UseFakeServer()
.UseKestrel()
.UseStartup<StartupHelloWorld>()
.Build();

View File

@ -1,4 +1,4 @@
using System;
using System;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting;
using Microsoft.AspNetCore.Http;
@ -20,8 +20,7 @@ namespace SampleStartups
public static void Main(string[] args)
{
var host = new WebHostBuilder()
//.UseKestrel()
.UseFakeServer()
.UseKestrel()
// Each of these three sets ApplicationName to the current assembly, which is needed in order to
// scan the assembly for HostingStartupAttributes.
// .UseSetting(WebHostDefaults.ApplicationKey, "SampleStartups")