Recenzie:
Începe prin a atașa adresa open source ASP.NET Core GitHub
Autentificarea cu hyperlink este vizibilă.
Autentificarea cu hyperlink este vizibilă.
După crearea unui nou proiect ASP.NET Core 3.1, codul programului este următorul:
Am analizat în detaliu codul de intrare combinat cu codul sursă de pe GitHub.
Cod gazdă:Autentificarea cu hyperlink este vizibilă.
Metoda CreateDefaultBuilder
Aici instanțiem un obiect HostBuilder, care moștenește din IHostBuilder, și adăugăm delegați definiți de sistem, cum ar fi :appsettings.json, appsettings. {env. EnvironmentName}.json fișier de configurare, care în cele din urmă va returna: interfața IHostBuilder.
Cod HostBuilder:Autentificarea cu hyperlink este vizibilă.
Metoda Build va fi în cele din urmă apelată.
Construcția publică IHost()
{ dacă (_hostBuilt) { throw new InvalidOperationException(SR. BuildCalled); } _hostBuilt = adevărat;
BuildHostConfiguration(); CreeazăGazdăMediu (); CreeazăHostConstructorContext(); BuildAppConfiguration(); CreateServiceProvider();
returnare _appServices.GetRequiredService<IHost>();
} Metoda BuildHostConfiguration
_hostConfiguration privat de Iconfiguration; IConfigurationBuilder configBuilder = noul ConfigurationBuilder() Cheamă delegatul să adauge configurația pe rând
Metoda CreateHostingEnvironment
mediu de găzduire privat _hostingEnvironment; _hostingEnvironment = noul GazdăMediu ()
{ ApplicationName = _hostConfiguration[HostDefaults.ApplicationKey], EnvironmentName = _hostConfiguration[HostDefaults.EnvironmentKey] ?? Medii. Producție, ContentRootPath = ResolveContentRootPath(_hostConfiguration[HostDefaults.ContentRootKey], AppContext.BaseDirectory), }; Metoda CreateHostBuilderContext
privat HostBuilderContext _hostBuilderContext; _hostBuilderContext = noul HostBuilderContext(Properties)
{ MediuGazdă = _hostingEnvironment, Configurație = _hostConfiguration }; Metoda BuildAppConfiguration
Integrează din nou informațiile de configurare
IConfigurationBuilder configBuilder = noul ConfigurationBuilder() . SetBasePath(_hostingEnvironment.ContentRootPath) . AddConfiguration(_hostConfiguration, shouldDisposeConfiguration: true); _appConfiguration = configBuilder.Build(); _hostBuilderContext.Configuration = _appConfiguration; Metoda CreateServiceProvider
var services = noua Colecție de servicii(); Înregistrează un serviciu, sună un delegat și adaugă un serviciu definit de utilizator.
Metoda de extensie GenericHostBuilderExtensions
Autentificarea cu hyperlink este vizibilă.
Metoda de extensie ConfigureWebHost
Pentru a înregistra GenericWebHostService ca serviciu backend:
Constructor. ConfigureServices((context, services) = > servicii. AddHostedService<GenericWebHostService>()); GenericWebHostService Code:Autentificarea cu hyperlink este vizibilă.
public async Task StartAsync(CancellationToken cancellationToken) { HostingEventSource.Log.HostStart();
var serverAddressesFeature = Server.Features.Get<IServerAddressesFeature>(); var addresses = serverAddressesFeature?. Adrese; dacă (adresează != null && !adrese. IsReadOnly & & adrese. Numără == 0) { var urls = Configuration[WebHostDefaults.ServerUrlsKey]; if (!string. IsNullOrEmpty(urls)) { FuncționalitateaAdreseServer!. PreferHostingUrls = WebHostUtilities.ParseBool(Configuration, WebHostDefaults.PreferHostingUrlsKey);
Foreach (valoarea var în URL-uri. Split('; ', StringSplitOptions.RemoveEmptyEntrries)) { adrese. Adaugă (valoare); } } }
RequestDelegate? aplicație = nul;
încearcă { var configure = Options.ConfigureApplication;
if (configure == null) { throw new InvalidOperationException($"No application configured. Vă rugăm să specificați o aplicație prin IWebHostBuilder.UseStartup, IWebHostBuilder.Configure sau specificarea asamblării de pornire prin {nameof(WebHostDefaults.StartupAssemblyKey)} în configurația gazdei web."); }
var builder = ApplicationBuilderFactory.CreateBuilder(Server.Features);
foreach (var filter în StartupFilters.Reverse()) { configure = filtru. Configure(configure); }
configure(builder);
Construiește pipeline-ul de cereri aplicație = constructor. Build(); } catch (excepție ex) { Logger.ApplicationError(ex);
dacă (! Opțiuni.WebHostOptions.CaptureStartupErrors) { aruncă; }
var showDetailedErrors = HostingEnvironment.IsDevelopment() || Options.WebHostOptions.DetailedErrors;
aplicație = ErrorPageBuilder.BuildErrorPageApplication(HostingEnvironment.ContentRootFileProvider, Logger, showDetailedErrors, ex); }
var httpApplication = new HostingApplication (application, Logger, DiagnosticListener, HttpContextFactory);
await Server.StartAsync(httpApplication, cancellationToken);
dacă (adresează != nul) { foreach (adresă var în adrese) { LifetimeLogger.ListeningOnAddress (adresă); } }
if (Logger.IsEnabled(LogLevel.Debug)) { foreach (var assembly în Options.WebHostOptions.GetFinalHostingStartupAssemblies()) { Logger.StartupAssemblyLoaded(assembly); } }
if (Options.HostingStartupExceptions != null) { foreach (var exception în Options.HostingStartupExceptions.InnerExceptions) { Logger.HostingStartupAssemblyError(exception); } } }
var webhostBuilder = new GenericWebHostBuilder(builder, webHostBuilderOptions); Autentificarea cu hyperlink este vizibilă.
Metoda de extensie WebHostBuilderExtensions
Oferă un obiect startupType pentru apelurile IWebHostBuilder.
acest IWebHostBuilder gazdăConstructor dacă (hostBuilder este ISupportsStartup suportăStartup)
{ return supportsStartup.UseStartup(startType);
} Autentificarea cu hyperlink este vizibilă.
GenericWebHostBuilder Metodă Privată GenericWebHostBuilder
Instanțiază dinamic obiectul nostru Startup:
instanță ?? = ActivatorUtilities.CreateInstance(noul HostServiceProvider(webHostBuilderContext), startType); Context. Proprietăți[_startupKey] = instanță; Caută metoda ConfigureServices
var configureServicesBuilder = StartupLoader.FindConfigureServicesDelegate(startupType, context. MediuGazdă.NumeÎnconjurător); var configureServices = configureServicesBuilder.Build(instance);
intern static ConfigureServicesBuilder FindConfigureServicesDelegate([DynamicallyAccessedMembers(StartupLinkerOptions.Accessibility)] Type startType, string environmentName) { var servicesMethod = FindMethod(startupType, "Configure{0}Services", environmentName, typeof(IServiceProvider), required: false) ?? FindMethod(startType, "Configure{0}Services", environmentName, typeof(void), required: false); returnează noul ConfigureServicesBuilder(servicesMethod); Caută metoda ConfigureContainer
var configureContainerBuilder = StartupLoader.FindConfigureContainerDelegate(startupType, context. MediuGazdă.NumeÎnconjurător);
intern static ConfigureContainerBuilder FindConfigureContainerDelegate([DynamicallyAccessedMembers(StartupLinkerOptions.Accessibility)] Tip startType, șir environmentName) { var configureMethod = FindMethod(startupType, "Configure{0}Container", environmentName, typeof(void), required: false); return new ConfigureContainerBuilder(configureMethod); } Caută metoda Configure
configureBuilder = StartupLoader.FindConfigureDelegate(startupType, context. MediuGazdă.NumeÎnconjurător);
intern static ConfigureBuilder FindConfigureDelegate([DynamicallyAccessedMembers(StartupLinkerOptions.Accessibility)] Type startupType, string environmentName)
{ var configureMethod = FindMethod(startupType, "Configure{0}", environmentName, typeof(void), required: true)!; return new ConfigureBuilder(configureMethod);
} Apelat prin metoda Build a ConfigureBuilder, codul sursă este următorul:
clasa privată ConfigureBuilder { public ConfigureBuilder(MethodInfo configure) { MethodInfo = configure; }
public MethodInfo MethodInfo { get; }
Public<IApplicationBuilder> Action Build (instanță de obiect) { return (applicationBuilder) => Invoke(instanță, applicationBuilder); }
private void Invoke (instanță de obiect, IApplicationBuilder builder) { var serviceProvider = builder. Servicii de aplicații; var parameterInfos = MethodInfo.GetParameters(); var parameters = new object[parameterInfos.Length]; pentru (var index = 0; index < parameterInfos.Length; index++) { var parameterInfo = parameterInfos[index]; if (parameterInfo.ParameterType == typeof(IApplicationBuilder)) { parametri[index] = constructor; } altfel { încearcă { parametri[index] = ServiceProvider.GetRequiredService(parameterInfo.ParameterType); } catch (excepție ex) { throw new InvalidOperationException( Resources.FormatMiddlewareFilter_ServiceResolutionFail( parameterInfo.ParameterType.FullName, parameterInfo.Name, MethodInfo.Name, MethodInfo.DeclaringType.FullName), ex); } } } MethodInfo.Invoke(instanță, parametri); } } Metoda de execuție
Adresa metodei de extensie HostingAbstractionsHostExtensions:
Autentificarea cu hyperlink este vizibilă.
În cele din urmă sună:
/// <summary> Rulează o aplicație și returnează o Sarcină care se finalizează doar când tokenul este declanșat sau când închiderea este declanșată. /// </summary> <param name="host">The <vezi cref="IHost"/> to run.</param> <param name="token">Tokenul care declanșează oprirea.</param> <returns><vezi cref="Task"/> care reprezintă operația asincronă.</returns> public static async Task RunAsync (this IHost host, CancellationToken token = implicit) { încearcă { Așteaptă gazda. StartAsync (token). ConfigureAwait (false);
Așteaptă gazda. WaitForShutdownAsync(token). ConfigureAwait (false); } în sfârșit { if (gazda este IAsyncDisposable asyncDisposable) { await asyncDisposable.DisposeAsync(). ConfigureAwait (false); } altfel { gazdă. Elimină(); }
} } Anterior, când construiam un serviciu, mă înregistram la serviciul IHost, iar codul este următorul:
servicii. <IHost>AddSingleton(_ => { returnează noul Intern.Host(_appServices, _appServices.GetRequiredService<IHostApplicationLifetime>(), _appServices.GetRequiredService<ILogger<Internal.Host>>(), _appServices.GetRequiredService<IHostLifetime>(), _appServices.GetRequiredService<IOptions<HostOptions>>()); }); Metoda StartAsync
Adresă:Autentificarea cu hyperlink este vizibilă.
public async Task StartAsync(CancellationToken cancellationToken = implicit) { _logger. Starting();
folosind var combinedCancellationTokenSource = CancellationTokenSource.CreateLinkedTokenSource(cancellationToken, _applicationLifetime.ApplicationStopping); CancellationToken combinedCancellationToken = combinedCancellationTokenSource.Token;
await _hostLifetime.WaitForStartAsync(combinedCancellationToken). ConfigureAwait (false);
CombinedCancellationToken.ThrowIfCancellationRequested(); _hostedServices = Services.GetService<IEnumerable<IHostedService>>();
foreach (IHostedService găzduit Service în _hostedServices) { // Fire IHostedService.Start await hostedService.StartAsync(combinedCancellationToken). ConfigureAwait (false);
if (hostedService este BackgroundService backgroundService) { _ = HandleBackgroundException(backgroundService); } }
// Fire IHostApplicationLifetime.Started _applicationLifetime.NotifyStarted();
_logger. A început(); } (Sfârșit)
|