Kestrel web server implementation in ASP.NET Core


Note

ASP.NET Core 2.1 is in preview and not recommended for production use.

By default, ASP.NET Core binds to:

  • http://localhost:5000
  • https://localhost:5001 (when a local development certificate is present)

A development certificate is created:

Some browsers require that you grant explicit permission to the browser to trust the local development certificate.

ASP.NET Core 2.1 and later project templates configure apps to run on HTTPS by default and include HTTPS redirection and HSTS support.

Call Listen or ListenUnixSocket methods on KestrelServerOptions to configure URL prefixes and ports for Kestrel.

UseUrls, the --urls command-line argument, urls host configuration key, and the ASPNETCORE_URLS environment variable also work but have the limitations noted later in this section (a default certificate must be available for HTTPS endpoint configuration).

ASP.NET Core 2.1 KestrelServerOptions configuration:

ConfigureEndpointDefaults(Action)
Specifies a configuration Action to run for each specified endpoint. Calling ConfigureEndpointDefaults multiple times replaces prior Actions with the last Action specified.

ConfigureHttpsDefaults(Action)
Specifies a configuration Action to run for each HTTPS endpoint. Calling ConfigureHttpsDefaults multiple times replaces prior Actions with the last Action specified.

Configure(IConfiguration)
Creates a configuration loader for setting up Kestrel that takes an IConfiguration as input. The configuration must be scoped to the configuration section for Kestrel.

ListenOptions.UseHttps
Configure Kestrel to use HTTPS.

ListenOptions.UseHttps extensions:

  • UseHttps – Configure Kestrel to use HTTPS with the default certificate. Throws an exception if no default certificate is configured.
  • UseHttps(string fileName)
  • UseHttps(string fileName, string password)
  • UseHttps(string fileName, string password, Action<HttpsConnectionAdapterOptions> configureOptions)
  • UseHttps(StoreName storeName, string subject)
  • UseHttps(StoreName storeName, string subject, bool allowInvalid)
  • UseHttps(StoreName storeName, string subject, bool allowInvalid, StoreLocation location)
  • UseHttps(StoreName storeName, string subject, bool allowInvalid, StoreLocation location, Action<HttpsConnectionAdapterOptions> configureOptions)
  • UseHttps(X509Certificate2 serverCertificate)
  • UseHttps(X509Certificate2 serverCertificate, Action<HttpsConnectionAdapterOptions> configureOptions)
  • UseHttps(Action<HttpsConnectionAdapterOptions> configureOptions)

ListenOptions.UseHttps parameters:

  • filename is the path and file name of a certificate file, relative to the directory that contains the app’s content files.
  • password is the password required to access the X.509 certificate data.
  • configureOptions is an Action to configure the HttpsConnectionAdapterOptions. Returns the ListenOptions.
  • storeName is the certificate store from which to load the certificate.
  • subject is the subject name for the certificate.
  • allowInvalid indicates if invalid certificates should be considered, such as self-signed certificates.
  • location is the store location to load the certificate from.
  • serverCertificate is the X.509 certificate.

In production, HTTPS must be explicitly configured. At a minimum, a default certificate must be provided.

Supported configurations described next:

  • No configuration
  • Replace the default certificate from configuration
  • Change the defaults in code

No configuration

Kestrel listens on http://localhost:5000 and https://localhost:5001 (if a default cert is available).

Specify URLs using the:

  • ASPNETCORE_URLS environment variable.
  • --urls command-line argument.
  • urls host configuration key.
  • UseUrls extension method.

For more information, see Server URLs and Overriding configuration.

The value provided using these approaches can be one or more HTTP and HTTPS endpoints (HTTPS if a default cert is available). Configure the value as a semicolon-separated list (for example, "Urls": "http://localhost:8000;http://localhost:8001").

Replace the default certificate from configuration

WebHost.CreateDefaultBuilder calls serverOptions.Configure(context.Configuration.GetSection("Kestrel")) by default to load Kestrel configuration. A default HTTPS app settings configuration schema is available for Kestrel. Configure multiple endpoints, including the URLs and the certificates to use, either from a file on disk or from a certificate store.

In the following appsettings.json example:

  • Set AllowInvalid to true to permit the use of invalid certificates (for example, self-signed certificates).
  • Any HTTPS endpoint that doesn’t specify a certificate (HttpsDefaultCert in the example that follows) falls back to the cert defined under Certificates > Default or the development certificate.
{
"Kestrel": 
"EndPoints": 
"Http": 
"Url": "http://localhost:5000"
,

"HttpsInlineCertFile": 
"Url": "https://localhost:5001",
"Certificate": 
"Path": "<path to .pfx file>",
"Password": "<certificate password>"

,

"HttpsInlineCertStore": 
"Url": "https://localhost:5002",
"Certificate": 
"Subject": "<subject; required>",
"Store": "<certificate store; defaults to My>",
"Location": "<location; defaults to CurrentUser>",
"AllowInvalid": "<true or false; defaults to false>"

,

"HttpsDefaultCert": 
"Url": "https://localhost:5003"
,

"Https": 
"Url": "https://*:5004",
"Certificate": 
"Path": "<path to .pfx file>",
"Password": "<certificate password>"


,
"Certificates": 
"Default": 
"Path": "<path to .pfx file>",
"Password": "<certificate password>"



}

An alternative to using Path and Password for any certificate node is to specify the certificate using certificate store fields. For example, the Certificates > Default certificate can be specified as:

"Default": 
"Subject": "<subject; required>",
"Store": "<cert store; defaults to My>",
"Location": "<location; defaults to CurrentUser>",
"AllowInvalid": "<true or false; defaults to false>"

Schema notes:

  • Endpoints names are case-insensitive. For example, HTTPS and Https are valid.
  • The Url parameter is required for each endpoint. The format for this parameter is the same as the top-level Urls configuration parameter except that it’s limited to a single value.
  • These endpoints replace those defined in the top-level Urls configuration rather than adding to them. Endpoints defined in code via Listen are cumulative with the endpoints defined in the configuration section.
  • The Certificate section is optional. If the Certificate section isn’t specified, the defaults defined in earlier scenarios are used. If no defaults are available, the server throws an exception and fails to start.
  • The Certificate section supports both PathPassword and SubjectStore certificates.
  • Any number of endpoints may be defined in this way so long as they don’t cause port conflicts.
  • serverOptions.Configure(context.Configuration.GetSection("Kestrel")) returns a KestrelConfigurationLoader with an .Endpoint(string name, options => ) method that can be used to supplement a configured endpoint’s settings:
serverOptions.Configure(context.Configuration.GetSection("Kestrel"))
.Endpoint("HTTPS", opt =>

opt.HttpsOptions.SslProtocols = SslProtocols.Tls12;
);

You can also directly access KestrelServerOptions.ConfigurationLoader to keep iterating on the existing loader, such as the one provided by WebHost.CreatedDeafaultBuilder.

  • The configuration section for each endpoint is a available on the options in the Endpoint method so that custom settings may be read.
  • Multiple configurations may be loaded by calling serverOptions.Configure(context.Configuration.GetSection("Kestrel")) again with another section. Only the last configuration is used, unless Load is explicitly called on prior instances. The metapackage doesn’t call Load so that its default configuration section may be replaced.
  • KestrelConfigurationLoader mirrors the Listen family of APIs from KestrelServerOptions as Endpoint overloads, so code and config endpoints may be configured in the same place. These overloads don’t use names and only consume default settings from configuration.

Change the defaults in code

ConfigureEndpointDefaults and ConfigureHttpsDefaults can be used to change default settings for ListenOptions and HttpsConnectionAdapterOptions, including overriding the default certificate specified in the prior scenario. ConfigureEndpointDefaults and ConfigureHttpsDefaults should be called before any endpoints are configured.

options.ConfigureEndpointDefaults(opt =>

opt.NoDelay = true;
);

options.ConfigureHttpsDefaults(httpsOptions =>

httpsOptions.SslProtocols = SslProtocols.Tls12;
);

Kestrel support for SNI

Server Name Indication (SNI) can be used to host multiple domains on the same IP address and port. For SNI to function, the client sends the host name for the secure session to the server during the TLS handshake so that the server can provide the correct certificate. The client uses the furnished certificate for encrypted communication with the server during the secure session that follows the TLS handshake.

Kestrel supports SNI via the ServerCertificateSelector callback. The callback is invoked once per connection to allow the app to inspect the host name and select the appropriate certificate.

SNI support requires running on target framework netcoreapp2.1. On netcoreapp2.0 and net461, the callback is invoked but the name is always null. The name is also null if the client doesn’t provide the host name parameter in the TLS handshake.

WebHost.CreateDefaultBuilder()
.UseKestrel((context, options) =>
{
options.ListenAnyIP(5005, listenOptions =>

listenOptions.UseHttps(httpsOptions =>

var localhostCert = CertificateLoader.LoadFromStoreCert(
"localhost", "My", StoreLocation.CurrentUser, 
allowInvalid: true);
var exampleCert = CertificateLoader.LoadFromStoreCert(
"example.com", "My", StoreLocation.CurrentUser, 
allowInvalid: true);
var subExampleCert = CertificateLoader.LoadFromStoreCert(
"sub.example.com", "My", StoreLocation.CurrentUser, 
allowInvalid: true);
var certs = new Dictionary(StringComparer.OrdinalIgnoreCase);
certs["localhost"] = localhostCert;
certs["example.com"] = exampleCert;
certs["sub.example.com"] = subExampleCert;

httpsOptions.ServerCertificateSelector = (connectionContext, name) =>

if (name != null && certs.TryGetValue(name, out var cert))

return cert;


return exampleCert;
;
);
);
});

The Listen method binds to a TCP socket, and an options lambda permits SSL certificate configuration:

Notice how this example configures SSL for a particular endpoint by using ListenOptions. Use the same API to configure other Kestrel settings for specific endpoints.

Listen on a Unix socket with ListenUnixSocket for improved performance with Nginx, as shown in this example:

When the port number 0 is specified, Kestrel dynamically binds to an available port. The following example shows how to determine which port Kestrel actually bound at runtime:

When the app is run, the console window output indicates the dynamic port where the app can be reached:

UseUrls, –urls command-line argument, urls host configuration key, and ASPNETCORE_URLS environment variable limitations

These methods are useful for making code work with servers other than Kestrel. However, be aware of these limitations:

When using IIS, the URL bindings for IIS override bindings are set by either Listen or UseUrls. For more information, see the ASP.NET Core Module topic.



source_link
https://www.asp.net