ASP.NET
Core HTTPS SSL
▌Introduction
Learn how
to force the ASP.NET Core application to redirect requests from HTTP to HTTPS.
▌Environment
▋.NET Core 2.2.104
▋Visual Studio 2017
Community
▌Implement
▋Visual Studio's template
The quickest way is enabling the option: Configure for HTTPS, while creating a
new project.
▋Enable HTTPS manually
In Startup.cs,
public void Configure(IApplicationBuilder
app, IHostingEnvironment env)
{
app.UseHttpsRedirection();
// ...Skip
}
▋(Option1)
Kestrel
※launchSettings.json
Update
the applicationUrl to
control the ports of Http and Https,
"profiles": {
"Demo.WebApi": {
"commandName": "Project",
"launchBrowser": true,
"environmentVariables": {
"ASPNETCORE_ENVIRONMENT": "Development"
},
"applicationUrl": "https://localhost:5001;http://localhost:5000"
},
}
▋(Option2) IIS
express
!! SSL Ports is limited to
44300 to 44399 in IIS Express.
(Reference: Handling URL Binding Failures in IIS Express) |
※launchSettings.json
Set the sslPort like following,
"iisSettings": {
"windowsAuthentication": false,
"anonymousAuthentication": true,
"iisExpress": {
"applicationUrl": "http://localhost:5000",
"sslPort": 44301
}
}
The
settings will be mapped to 【.vs\config\applicationhost.config】
<site name="Demo.Web" id="2">
<application path="/" applicationPool="Demo.WebApi
AppPool">
<virtualDirectory path="/" physicalPath="D:\Works\SourceControl\...\Demo.Web" />
</application>
<bindings>
<binding protocol="http" bindingInformation="*:5000:localhost" />
<binding protocol="https" bindingInformation="*:44301:localhost" />
</bindings>
</site>
And while
you runs the application on IIS Express, the system environment variable:
ASPNETCORE_HTTPS_PORT
Will be
put into WebConfig as following.
<system.webServer>
<aspNetCore processPath="%LAUNCHER_PATH%" arguments="%LAUNCHER_ARGS%" stdoutLogEnabled="true" stdoutLogFile=".\App_Data\stdout" hostingModel="InProcess">
<environmentVariables>
<environmentVariable name="ASPNETCORE_HTTPS_PORT" value="5556" />
</environmentVariables>
</aspNetCore>
</system.webServer>
▋Http.Sys in IIS/IIS Express
Http.Sys on IIS
Express will default supports Https.
※launchSettings.json
Set sslPort in
iisSettings.
{
"iisSettings": {
"windowsAuthentication": true,
"anonymousAuthentication": true,
"iisExpress": {
"applicationUrl": "http://localhost:61598/",
"sslPort": 44301
}
},
}
※Program.cs
public static IWebHostBuilder CreateWebHostBuilder(string[] args)
=>
WebHost.CreateDefaultBuilder(args)
.UseStartup<Startup>()
.UseIISIntegration()
// …
}
※Startup.cs
public void ConfigureServices(IServiceCollection services)
{
#region
Enable Authentication by Http.Sys
services.AddAuthentication(HttpSysDefaults.AuthenticationScheme);
#endregion
}
▋Http.Sys by self-hosting
Http.Sys by self-hosting cannot use
Https directly. We have to manually bind the SSL certificate to the site.
|
1. First
find out the hash code (Thumbprint)
of the target SSL cert by certlm.msc as following.
---
Notice that the SSL cert MUST be in Local Machine level, or you will get the error message when doing netsh http add sslcert … later.
SSL Certificate add failed, Error 1312
A specified logon session does not exist. It may already have been terminated.
|
See reference on StackOverflow.
---
2. SSL cert binding and Url reservation
Then use the powershell command to bind the SSL cert to our host:port.
Then use the powershell command to bind the SSL cert to our host:port.
$guid = [guid]::NewGuid()
$certHash = "da787c5xxxxxxxxxxxxxxxxxxxxxxxxxx9ab3"
$ip = "0.0.0.0" #
This means all IP addresses
$port = "5001" #
the default HTTPS port
"http add sslcert ipport=$($ip):$port
certhash=$certHash appid={$guid}" |
netsh
"http add urlacl url=https://+:5001/
user=""NT AUTHORITY\NETWORK
SERVICE""" |
netsh
And then set
the URL reservation for the specified URL namespace for the DOMAIN\user account.
"http add urlacl url=https://+:5001/
user=""NT
AUTHORITY\NETWORK SERVICE""" | netsh
If you get the error:
“Access is denied”
When starting the Http.Sys server, try REMOVING the
urlacl!
|
You can
check the list of URL reservations(urlacl) by
"http show urlacl" | netsh
Or remove
the urlacl by
"http delete urlacl url=https://+:5001/" | netsh
3. Update code
※Program.cs
public static IWebHostBuilder CreateWebHostBuilder(string[] args)
=>
WebHost.CreateDefaultBuilder(args)
.UseStartup<Startup>()
.UseHttpSys(options
=>
{
options.Authentication.Schemes =
AuthenticationSchemes.NTLM | AuthenticationSchemes.Negotiate;
options.Authentication.AllowAnonymous = true;
options.MaxConnections = null;
options.MaxRequestBodySize = 30000000;
options.UrlPrefixes.Add("http://localhost:5000");
options.UrlPrefixes.Add("https://localhost:5001");
})
// …
}
※Startup.cs
public void ConfigureServices(IServiceCollection services)
{
#region
Enable Authentication by Http.Sys
services.AddAuthentication(
Microsoft.AspNetCore.Server.IISIntegration.IISDefaults.AuthenticationScheme);
#endregion
}
▌On Production
▋IIS : (Option1) HTTPS Redirection Middleware
The
default redirection is 307
Temporary Redirect.
If you
wanna change the redirection as 308
Permanent Redirect, use AddHttpsRedirection
to configure middleware options.
※Startup.cs
public void ConfigureServices(IServiceCollection
services)
{
services.AddMvc();
if (!this._env.IsDevelopment())
{
services.AddHttpsRedirection(options =>
{
options.RedirectStatusCode = StatusCodes.Status308PermanentRedirect;
options.HttpsPort = 443;
});
}
}
Notice that using HttpsRedirectionOptions.HttpsPort will overwrite ASPNETCORE_HTTPS_PORT environment variable’s value. Make sure one of them is set for enabling HTTPS. |
Then,
1. Set the system environment variable: ASPNETCORE_ENVIRONMENT
2. To override the system environment variable (Reference),
set it on WebConfig like following,
<aspNetCore processPath="dotnet"
arguments=".\MyApp.dll"
stdoutLogEnabled="false"
stdoutLogFile=".\log\stdout"
hostingModel="InProcess">
<environmentVariables>
<environmentVariable name="ASPNETCORE_ENVIRONMENT" value="Staging" />
</environmentVariables>
</aspNetCore>
Notice that setting both System environment variable and WebConfig, will get a concat value, for example, Staging;Production.
Follow issue#6140.
|
3. The value of ASPNETCORE_ENVIRONMENT
in WebConfig can be set in Publish Profile (*.pubxml) as well for
deployment.
<PropertyGroup>
<EnvironmentName>Production</EnvironmentName>
</PropertyGroup>
Then we
can deploy by,
$ dotnet publish --configuration Release /p:PublishProfile=Properties\PublishProfiles\FolderProfile.pubxml
▋IIS : (Option2) Redirect rules on WebConfig
URL Rewrite module is required.
|
▋For
localhost/IP:Port
<system.webServer>
<rewrite>
<rules>
<rule name="HTTP
to HTTPS redirect" stopProcessing="true">
<match url=".*" />
<conditions>
<add input="{HTTP_HOST}" pattern="^(.*):2222$" />
</conditions>
<action type="Redirect" url="https://{C:1}:2223/{R:0}" redirectType="Temporary" />
</rule>
</rules>
</rewrite>
</system.webServer>
▋Already has a
Domain name
<system.webServer>
<rewrite>
<rules>
<rule name="HTTP
to HTTPS redirect" stopProcessing="true">
<match url="(.*)" />
<conditions>
<add input="{HTTPS}" pattern="off" ignoreCase="true" />
</conditions>
<action type="Redirect" redirectType="Found" url="https://{HTTP_HOST}/{R:1}" redirectType="Temporary" />
</rule>
</rules>
</rewrite>
</system.webServer>
▌Reference
沒有留言:
張貼留言