Add Basic auth tests and fix Windows auth tests (#1502)
This commit is contained in:
parent
fc40985dff
commit
642e8e9d7c
|
|
@ -41,14 +41,40 @@ namespace Microsoft.AspNetCore.Server.IntegrationTesting.IIS
|
|||
});
|
||||
}
|
||||
|
||||
public static void AddWindowsAuthToServerConfig(this IISDeploymentParameters parameters)
|
||||
public static void SetWindowsAuth(this IISDeploymentParameters parameters, bool enabled = true)
|
||||
{
|
||||
parameters.EnableModule("WindowsAuthenticationModule", "%IIS_BIN%\\authsspi.dll");
|
||||
|
||||
parameters.AddServerConfigAction(
|
||||
element =>
|
||||
{
|
||||
element.Descendants("windowsAuthentication")
|
||||
.Single()
|
||||
.SetAttributeValue("enabled", "true");
|
||||
.SetAttributeValue("enabled", enabled);
|
||||
});
|
||||
}
|
||||
|
||||
public static void SetAnonymousAuth(this IISDeploymentParameters parameters, bool enabled = true)
|
||||
{
|
||||
parameters.AddServerConfigAction(
|
||||
element =>
|
||||
{
|
||||
element.Descendants("anonymousAuthentication")
|
||||
.Single()
|
||||
.SetAttributeValue("enabled", enabled);
|
||||
});
|
||||
}
|
||||
|
||||
public static void SetBasicAuth(this IISDeploymentParameters parameters, bool enabled = true)
|
||||
{
|
||||
parameters.EnableModule("BasicAuthenticationModule", "%IIS_BIN%\\authbas.dll");
|
||||
|
||||
parameters.AddServerConfigAction(
|
||||
element =>
|
||||
{
|
||||
element.Descendants("basicAuthentication")
|
||||
.Single()
|
||||
.SetAttributeValue("enabled", enabled);
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -66,7 +66,7 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
|||
response = await deploymentResult.HttpClient.GetAsync("/Auth");
|
||||
responseText = await response.Content.ReadAsStringAsync();
|
||||
|
||||
Assert.True("null".Equals(responseText), "Auth");
|
||||
Assert.Equal("null", responseText);
|
||||
|
||||
Assert.Equal(
|
||||
$"ContentRootPath {deploymentResult.ContentRoot}" + Environment.NewLine +
|
||||
|
|
|
|||
|
|
@ -16,6 +16,7 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
|||
DynamicCompression = 16,
|
||||
ApplicationInitialization = 32,
|
||||
TracingModule = 64,
|
||||
FailedRequestTracingModule = 128
|
||||
FailedRequestTracingModule = 128,
|
||||
BasicAuthentication = 256
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -15,16 +15,21 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
|||
[AttributeUsage(AttributeTargets.Assembly | AttributeTargets.Class | AttributeTargets.Method)]
|
||||
public sealed class RequiresIISAttribute : Attribute, ITestCondition
|
||||
{
|
||||
private static readonly (IISCapability Capability, string DllName)[] Modules =
|
||||
{
|
||||
(IISCapability.Websockets, "iiswsock.dll"),
|
||||
(IISCapability.WindowsAuthentication, "authsspi.dll"),
|
||||
(IISCapability.DynamicCompression, "compdyn.dll"),
|
||||
(IISCapability.ApplicationInitialization, "warmup.dll"),
|
||||
(IISCapability.TracingModule, "iisetw.dll"),
|
||||
(IISCapability.FailedRequestTracingModule, "iisfreb.dll"),
|
||||
(IISCapability.BasicAuthentication, "authbas.dll"),
|
||||
};
|
||||
|
||||
private static readonly bool _isMetStatic;
|
||||
private static readonly string _skipReasonStatic;
|
||||
|
||||
private static readonly bool _websocketsAvailable;
|
||||
private static readonly bool _windowsAuthAvailable;
|
||||
private static readonly bool _poolEnvironmentVariablesAvailable;
|
||||
private static readonly bool _dynamicCompressionAvailable;
|
||||
private static readonly bool _applicationInitializationModule;
|
||||
private static readonly bool _tracingModuleAvailable;
|
||||
private static readonly bool _frebTracingModuleAvailable;
|
||||
private static readonly IISCapability _modulesAvailable;
|
||||
|
||||
static RequiresIISAttribute()
|
||||
{
|
||||
|
|
@ -81,18 +86,13 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
|||
|
||||
_skipReasonStatic = _isMetStatic ? null : "IIS schema needs to be upgraded to support ANCM.";
|
||||
|
||||
_websocketsAvailable = File.Exists(Path.Combine(Environment.SystemDirectory, "inetsrv", "iiswsock.dll"));
|
||||
|
||||
_windowsAuthAvailable = File.Exists(Path.Combine(Environment.SystemDirectory, "inetsrv", "authsspi.dll"));
|
||||
|
||||
_dynamicCompressionAvailable = File.Exists(Path.Combine(Environment.SystemDirectory, "inetsrv", "compdyn.dll"));
|
||||
|
||||
_applicationInitializationModule = File.Exists(Path.Combine(Environment.SystemDirectory, "inetsrv", "warmup.dll"));
|
||||
|
||||
_tracingModuleAvailable = File.Exists(Path.Combine(Environment.SystemDirectory, "inetsrv", "iisetw.dll"));
|
||||
|
||||
_frebTracingModuleAvailable = File.Exists(Path.Combine(Environment.SystemDirectory, "inetsrv", "iisfreb.dll"));
|
||||
|
||||
foreach (var module in Modules)
|
||||
{
|
||||
if (File.Exists(Path.Combine(Environment.SystemDirectory, "inetsrv", module.DllName)))
|
||||
{
|
||||
_modulesAvailable |= module.Capability;
|
||||
}
|
||||
}
|
||||
|
||||
var iisRegistryKey = Registry.LocalMachine.OpenSubKey(@"Software\Microsoft\InetStp", writable: false);
|
||||
if (iisRegistryKey == null)
|
||||
|
|
@ -115,23 +115,6 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
|||
{
|
||||
IsMet = _isMetStatic;
|
||||
SkipReason = _skipReasonStatic;
|
||||
if (capabilities.HasFlag(IISCapability.Websockets))
|
||||
{
|
||||
IsMet &= _websocketsAvailable;
|
||||
if (!_websocketsAvailable)
|
||||
{
|
||||
SkipReason += "The machine does not have IIS websockets installed.";
|
||||
}
|
||||
}
|
||||
if (capabilities.HasFlag(IISCapability.WindowsAuthentication))
|
||||
{
|
||||
IsMet &= _windowsAuthAvailable;
|
||||
|
||||
if (!_windowsAuthAvailable)
|
||||
{
|
||||
SkipReason += "The machine does not have IIS windows authentication installed.";
|
||||
}
|
||||
}
|
||||
if (capabilities.HasFlag(IISCapability.PoolEnvironmentVariables))
|
||||
{
|
||||
IsMet &= _poolEnvironmentVariablesAvailable;
|
||||
|
|
@ -147,40 +130,16 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
|||
SkipReason += "https://github.com/aspnet/IISIntegration/issues/1074";
|
||||
}
|
||||
|
||||
if (capabilities.HasFlag(IISCapability.DynamicCompression))
|
||||
foreach (var module in Modules)
|
||||
{
|
||||
IsMet &= _dynamicCompressionAvailable;
|
||||
if (!_dynamicCompressionAvailable)
|
||||
if (capabilities.HasFlag(module.Capability))
|
||||
{
|
||||
SkipReason += "The machine does not have IIS dynamic compression installed.";
|
||||
}
|
||||
}
|
||||
|
||||
if (capabilities.HasFlag(IISCapability.ApplicationInitialization))
|
||||
{
|
||||
IsMet &= _applicationInitializationModule;
|
||||
if (!_applicationInitializationModule)
|
||||
{
|
||||
SkipReason += "The machine does not have IIS ApplicationInitialization installed.";
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
if (capabilities.HasFlag(IISCapability.TracingModule))
|
||||
{
|
||||
IsMet &= _tracingModuleAvailable;
|
||||
if (!_tracingModuleAvailable)
|
||||
{
|
||||
SkipReason += "The machine does not have IIS Failed Request Tracing Module installed.";
|
||||
}
|
||||
}
|
||||
|
||||
if (capabilities.HasFlag(IISCapability.FailedRequestTracingModule))
|
||||
{
|
||||
IsMet &= _frebTracingModuleAvailable;
|
||||
if (!_frebTracingModuleAvailable)
|
||||
{
|
||||
SkipReason += "The machine does not have IIS Failed Request Tracing Module installed.";
|
||||
var available = _modulesAvailable.HasFlag(module.Capability);
|
||||
IsMet &= available;
|
||||
if (!available)
|
||||
{
|
||||
SkipReason += $"The machine does have {module.Capability} available.";
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -0,0 +1,70 @@
|
|||
// 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;
|
||||
using System.Net.Http;
|
||||
using System.Net.Http.Headers;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.AspNetCore.Server.IIS.FunctionalTests.Utilities;
|
||||
using Microsoft.AspNetCore.Server.IntegrationTesting;
|
||||
using Microsoft.AspNetCore.Server.IntegrationTesting.IIS;
|
||||
using Microsoft.AspNetCore.Testing.xunit;
|
||||
using Xunit;
|
||||
|
||||
namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
||||
{
|
||||
[Collection(PublishedSitesCollection.Name)]
|
||||
public class BasicAuthTests : IISFunctionalTestBase
|
||||
{
|
||||
private readonly PublishedSitesFixture _fixture;
|
||||
|
||||
public BasicAuthTests(PublishedSitesFixture fixture)
|
||||
{
|
||||
_fixture = fixture;
|
||||
}
|
||||
|
||||
public static TestMatrix TestVariants
|
||||
=> TestMatrix.ForServers(DeployerSelector.ServerType)
|
||||
.WithTfms(Tfm.NetCoreApp22)
|
||||
.WithApplicationTypes(ApplicationType.Portable)
|
||||
.WithAllAncmVersions()
|
||||
.WithAllHostingModels();
|
||||
|
||||
[ConditionalTheory(Skip = "This test is manual. To run it set ASPNETCORE_MODULE_TEST_USER and ASPNETCORE_MODULE_TEST_PASSWORD environment variables to existing user")]
|
||||
[RequiresIIS(IISCapability.BasicAuthentication)]
|
||||
[MemberData(nameof(TestVariants))]
|
||||
public async Task BasicAuthTest(TestVariant variant)
|
||||
{
|
||||
var username = Environment.GetEnvironmentVariable("ASPNETCORE_MODULE_TEST_USER");
|
||||
var password = Environment.GetEnvironmentVariable("ASPNETCORE_MODULE_TEST_PASSWORD");
|
||||
|
||||
var deploymentParameters = _fixture.GetBaseDeploymentParameters(variant, publish: true);
|
||||
deploymentParameters.SetAnonymousAuth(enabled: false);
|
||||
deploymentParameters.SetWindowsAuth(enabled: false);
|
||||
deploymentParameters.SetBasicAuth(enabled: true);
|
||||
|
||||
// The default in hosting sets windows auth to true.
|
||||
var deploymentResult = await DeployAsync(deploymentParameters);
|
||||
var request = new HttpRequestMessage(HttpMethod.Get, "/Auth");
|
||||
var byteArray = new UTF8Encoding().GetBytes(username + ":" + password);
|
||||
request.Headers.Authorization = new AuthenticationHeaderValue("Basic", Convert.ToBase64String(byteArray));
|
||||
|
||||
var response = await deploymentResult.HttpClient.SendAsync(request);
|
||||
|
||||
var responseText = await response.Content.ReadAsStringAsync();
|
||||
|
||||
if (variant.HostingModel == HostingModel.InProcess)
|
||||
{
|
||||
Assert.StartsWith("Windows", responseText);
|
||||
Assert.Contains(username, responseText);
|
||||
}
|
||||
else
|
||||
{
|
||||
// We expect out-of-proc not allowing basic auth
|
||||
Assert.Equal("Windows:", responseText);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -22,10 +22,11 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
|||
}
|
||||
|
||||
[ConditionalFact]
|
||||
[RequiresIIS(IISCapability.WindowsAuthentication)]
|
||||
public async Task Authentication_InProcess()
|
||||
{
|
||||
var deploymentParameters = _fixture.GetBaseDeploymentParameters(publish: true);
|
||||
deploymentParameters.AddWindowsAuthToServerConfig();
|
||||
deploymentParameters.SetWindowsAuth();
|
||||
|
||||
var deploymentResult = await DeployAsync(deploymentParameters);
|
||||
|
||||
|
|
|
|||
|
|
@ -34,13 +34,14 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
|||
.WithAllAncmVersions();
|
||||
|
||||
[ConditionalTheory]
|
||||
[RequiresIIS(IISCapability.WindowsAuthentication)]
|
||||
[MemberData(nameof(TestVariants))]
|
||||
public async Task NtlmAuthentication(TestVariant variant)
|
||||
{
|
||||
var deploymentParameters = _fixture.GetBaseDeploymentParameters(variant);
|
||||
deploymentParameters.ApplicationBaseUriHint = $"https://localhost:0/";
|
||||
|
||||
deploymentParameters.AddWindowsAuthToServerConfig();
|
||||
deploymentParameters.SetWindowsAuth(enabled: true);
|
||||
|
||||
var result = await DeployAsync(deploymentParameters);
|
||||
var response = await result.HttpClient.GetAsync("/HelloWorld");
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
|||
|
||||
public RequiresIISAttribute(IISCapability capabilities)
|
||||
{
|
||||
// IISCapabilities aren't pretinent to IISExpress
|
||||
// IISCapabilities aren't pertinent to IISExpress
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,6 +1,8 @@
|
|||
// 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;
|
||||
using System.Net.Http;
|
||||
using System.Threading.Tasks;
|
||||
using Microsoft.AspNetCore.Server.IIS.FunctionalTests.Utilities;
|
||||
using Microsoft.AspNetCore.Server.IntegrationTesting;
|
||||
|
|
@ -23,24 +25,28 @@ namespace Microsoft.AspNetCore.Server.IISIntegration.FunctionalTests
|
|||
public static TestMatrix TestVariants
|
||||
=> TestMatrix.ForServers(DeployerSelector.ServerType)
|
||||
.WithTfms(Tfm.NetCoreApp22, Tfm.Net461)
|
||||
.WithAllApplicationTypes()
|
||||
.WithApplicationTypes(ApplicationType.Portable)
|
||||
.WithAllAncmVersions()
|
||||
.WithAllHostingModels();
|
||||
|
||||
[ConditionalTheory]
|
||||
[RequiresIIS(IISCapability.WindowsAuthentication)]
|
||||
[MemberData(nameof(TestVariants))]
|
||||
public async Task WindowsAuthTest(TestVariant variant)
|
||||
{
|
||||
var deploymentParameters = _fixture.GetBaseDeploymentParameters(variant);
|
||||
deploymentParameters.AddWindowsAuthToServerConfig();
|
||||
deploymentParameters.SetAnonymousAuth(enabled: false);
|
||||
deploymentParameters.SetWindowsAuth();
|
||||
|
||||
// The default in hosting sets windows auth to true.
|
||||
var deploymentResult = await DeployAsync(deploymentParameters);
|
||||
|
||||
var response = await deploymentResult.HttpClient.GetAsync("/Auth");
|
||||
var client = deploymentResult.CreateClient(new HttpClientHandler { UseDefaultCredentials = true });
|
||||
var response = await client.GetAsync("/Auth");
|
||||
var responseText = await response.Content.ReadAsStringAsync();
|
||||
|
||||
Assert.Equal("Windows", responseText);
|
||||
Assert.StartsWith("Windows:", responseText);
|
||||
Assert.Contains(Environment.UserName, responseText);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -44,6 +44,10 @@ namespace TestSite
|
|||
var authScheme = (await authProvider.GetAllSchemesAsync()).SingleOrDefault();
|
||||
|
||||
await ctx.Response.WriteAsync(authScheme?.Name ?? "null");
|
||||
if (ctx.User.Identity.Name != null)
|
||||
{
|
||||
await ctx.Response.WriteAsync(":" + ctx.User.Identity.Name);
|
||||
}
|
||||
}
|
||||
|
||||
public async Task GetClientCert(HttpContext context)
|
||||
|
|
|
|||
Loading…
Reference in New Issue