#2 Platform handler middleware, sample, tests, functional tests.
This commit is contained in:
parent
1dc5764c74
commit
4510d20a83
|
|
@ -0,0 +1,65 @@
|
||||||
|
|
||||||
|
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||||
|
# Visual Studio 14
|
||||||
|
VisualStudioVersion = 14.0.23107.0
|
||||||
|
MinimumVisualStudioVersion = 10.0.40219.1
|
||||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "src", "src", "{04B1EDB6-E967-4D25-89B9-E6F8304038CD}"
|
||||||
|
EndProject
|
||||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Solution Items", "Solution Items", "{0EF45656-B25D-40D8-959C-726EAF185E60}"
|
||||||
|
ProjectSection(SolutionItems) = preProject
|
||||||
|
global.json = global.json
|
||||||
|
NuGet.Config = NuGet.Config
|
||||||
|
EndProjectSection
|
||||||
|
EndProject
|
||||||
|
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "Microsoft.AspNet.IISPlatformHandler", "src\Microsoft.AspNet.IISPlatformHandler\Microsoft.AspNet.IISPlatformHandler.xproj", "{ABE53415-83CE-4AF0-AF67-E52160C7862B}"
|
||||||
|
EndProject
|
||||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "test", "test", "{EF30B533-D715-421A-92B7-92FEF460AC9C}"
|
||||||
|
EndProject
|
||||||
|
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "Microsoft.AspNet.IISPlatformHandler.Tests", "test\Microsoft.AspNet.IISPlatformHandler.Tests\Microsoft.AspNet.IISPlatformHandler.Tests.xproj", "{FBBBE015-1CE3-454B-9647-23F8073FB7AB}"
|
||||||
|
EndProject
|
||||||
|
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "Microsoft.AspNet.IISPlatformHandler.FunctionalTests", "test\Microsoft.AspNet.IISPlatformHandler.FunctionalTests\Microsoft.AspNet.IISPlatformHandler.FunctionalTests.xproj", "{A83A33D1-3D29-403C-9750-5811AC7B4025}"
|
||||||
|
EndProject
|
||||||
|
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "TestSites", "test\TestSites\TestSites.xproj", "{E27453AD-9CA0-49A2-94FA-96337D77677D}"
|
||||||
|
EndProject
|
||||||
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "samples", "samples", "{C74B8F36-FD2F-45C9-9B8A-00E7CF0126A9}"
|
||||||
|
EndProject
|
||||||
|
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "IISSample", "samples\IISSample\IISSample.xproj", "{E4E2BDC4-A9C6-4AE9-B429-032EC83EDE64}"
|
||||||
|
EndProject
|
||||||
|
Global
|
||||||
|
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||||
|
Debug|Any CPU = Debug|Any CPU
|
||||||
|
Release|Any CPU = Release|Any CPU
|
||||||
|
EndGlobalSection
|
||||||
|
GlobalSection(ProjectConfigurationPlatforms) = postSolution
|
||||||
|
{ABE53415-83CE-4AF0-AF67-E52160C7862B}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{ABE53415-83CE-4AF0-AF67-E52160C7862B}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{ABE53415-83CE-4AF0-AF67-E52160C7862B}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{ABE53415-83CE-4AF0-AF67-E52160C7862B}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{FBBBE015-1CE3-454B-9647-23F8073FB7AB}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{FBBBE015-1CE3-454B-9647-23F8073FB7AB}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{FBBBE015-1CE3-454B-9647-23F8073FB7AB}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{FBBBE015-1CE3-454B-9647-23F8073FB7AB}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{A83A33D1-3D29-403C-9750-5811AC7B4025}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{A83A33D1-3D29-403C-9750-5811AC7B4025}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{A83A33D1-3D29-403C-9750-5811AC7B4025}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{A83A33D1-3D29-403C-9750-5811AC7B4025}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{E27453AD-9CA0-49A2-94FA-96337D77677D}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{E27453AD-9CA0-49A2-94FA-96337D77677D}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{E27453AD-9CA0-49A2-94FA-96337D77677D}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{E27453AD-9CA0-49A2-94FA-96337D77677D}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
{E4E2BDC4-A9C6-4AE9-B429-032EC83EDE64}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
|
{E4E2BDC4-A9C6-4AE9-B429-032EC83EDE64}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
|
{E4E2BDC4-A9C6-4AE9-B429-032EC83EDE64}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||||
|
{E4E2BDC4-A9C6-4AE9-B429-032EC83EDE64}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||||
|
EndGlobalSection
|
||||||
|
GlobalSection(SolutionProperties) = preSolution
|
||||||
|
HideSolutionNode = FALSE
|
||||||
|
EndGlobalSection
|
||||||
|
GlobalSection(NestedProjects) = preSolution
|
||||||
|
{ABE53415-83CE-4AF0-AF67-E52160C7862B} = {04B1EDB6-E967-4D25-89B9-E6F8304038CD}
|
||||||
|
{FBBBE015-1CE3-454B-9647-23F8073FB7AB} = {EF30B533-D715-421A-92B7-92FEF460AC9C}
|
||||||
|
{A83A33D1-3D29-403C-9750-5811AC7B4025} = {EF30B533-D715-421A-92B7-92FEF460AC9C}
|
||||||
|
{E27453AD-9CA0-49A2-94FA-96337D77677D} = {EF30B533-D715-421A-92B7-92FEF460AC9C}
|
||||||
|
{E4E2BDC4-A9C6-4AE9-B429-032EC83EDE64} = {C74B8F36-FD2F-45C9-9B8A-00E7CF0126A9}
|
||||||
|
EndGlobalSection
|
||||||
|
EndGlobal
|
||||||
|
|
@ -31,7 +31,9 @@ IF %BUILDCMD_DNX_VERSION%=="" (
|
||||||
) ELSE (
|
) ELSE (
|
||||||
CALL packages\KoreBuild\build\dnvm install %BUILDCMD_DNX_VERSION% -runtime CLR -arch x86 -a default
|
CALL packages\KoreBuild\build\dnvm install %BUILDCMD_DNX_VERSION% -runtime CLR -arch x86 -a default
|
||||||
)
|
)
|
||||||
|
CALL packages\KoreBuild\build\dnvm install default -arch x64
|
||||||
CALL packages\KoreBuild\build\dnvm install default -runtime CoreCLR -arch x86
|
CALL packages\KoreBuild\build\dnvm install default -runtime CoreCLR -arch x86
|
||||||
|
CALL packages\KoreBuild\build\dnvm install default -runtime CoreCLR -arch x64
|
||||||
|
|
||||||
:run
|
:run
|
||||||
CALL packages\KoreBuild\build\dnvm use default -runtime CLR -arch x86
|
CALL packages\KoreBuild\build\dnvm use default -runtime CLR -arch x86
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,19 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<Project ToolsVersion="14.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||||
|
<PropertyGroup>
|
||||||
|
<VisualStudioVersion Condition="'$(VisualStudioVersion)' == ''">14.0</VisualStudioVersion>
|
||||||
|
<VSToolsPath Condition="'$(VSToolsPath)' == ''">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)</VSToolsPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.Props" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
<PropertyGroup Label="Globals">
|
||||||
|
<ProjectGuid>e4e2bdc4-a9c6-4ae9-b429-032ec83ede64</ProjectGuid>
|
||||||
|
<RootNamespace>IISSample</RootNamespace>
|
||||||
|
<BaseIntermediateOutputPath Condition="'$(BaseIntermediateOutputPath)'=='' ">..\..\artifacts\obj\$(MSBuildProjectName)</BaseIntermediateOutputPath>
|
||||||
|
<OutputPath Condition="'$(OutputPath)'=='' ">..\..\artifacts\bin\$(MSBuildProjectName)\</OutputPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
<PropertyGroup>
|
||||||
|
<SchemaVersion>2.0</SchemaVersion>
|
||||||
|
<DevelopmentServerPort>65029</DevelopmentServerPort>
|
||||||
|
</PropertyGroup>
|
||||||
|
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.targets" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
</Project>
|
||||||
|
|
@ -0,0 +1,30 @@
|
||||||
|
using System;
|
||||||
|
using Microsoft.AspNet.Builder;
|
||||||
|
using Microsoft.AspNet.Http;
|
||||||
|
using Microsoft.Framework.Logging;
|
||||||
|
|
||||||
|
namespace IISSample
|
||||||
|
{
|
||||||
|
public class Startup
|
||||||
|
{
|
||||||
|
public void Configure(IApplicationBuilder app, ILoggerFactory loggerfactory)
|
||||||
|
{
|
||||||
|
loggerfactory.AddConsole(LogLevel.Verbose);
|
||||||
|
|
||||||
|
var logger = loggerfactory.CreateLogger("Requests");
|
||||||
|
|
||||||
|
app.Run(async (context) =>
|
||||||
|
{
|
||||||
|
logger.LogVerbose("Received request: " + context.Request.Method + " " + context.Request.Path);
|
||||||
|
|
||||||
|
context.Response.ContentType = "text/plain";
|
||||||
|
await context.Response.WriteAsync("Hello World - " + DateTimeOffset.Now + Environment.NewLine);
|
||||||
|
await context.Response.WriteAsync("User - " + context.User.Identity.Name + Environment.NewLine);
|
||||||
|
foreach (var header in context.Request.Headers)
|
||||||
|
{
|
||||||
|
await context.Response.WriteAsync(header.Key + ": " + header.Value + Environment.NewLine);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,34 @@
|
||||||
|
{
|
||||||
|
"webroot": "wwwroot",
|
||||||
|
"version": "1.0.0-*",
|
||||||
|
|
||||||
|
"dependencies": {
|
||||||
|
"Microsoft.AspNet.IISPlatformHandler": "1.0.0-*",
|
||||||
|
"Microsoft.AspNet.Server.Kestrel": "1.0.0-*",
|
||||||
|
"Microsoft.AspNet.Server.WebListener": "1.0.0-*",
|
||||||
|
"Microsoft.Framework.Logging.Console": "1.0.0-*"
|
||||||
|
},
|
||||||
|
|
||||||
|
"commands": {
|
||||||
|
"weblistener": "Microsoft.AspNet.Server.WebListener",
|
||||||
|
"web": "Microsoft.AspNet.Server.Kestrel"
|
||||||
|
},
|
||||||
|
|
||||||
|
"frameworks": {
|
||||||
|
"dnx451": { },
|
||||||
|
"dnxcore50": { }
|
||||||
|
},
|
||||||
|
|
||||||
|
"publishExclude": [
|
||||||
|
"node_modules",
|
||||||
|
"bower_components",
|
||||||
|
"**.xproj",
|
||||||
|
"**.user",
|
||||||
|
"**.vspscc"
|
||||||
|
],
|
||||||
|
"exclude": [
|
||||||
|
"wwwroot",
|
||||||
|
"node_modules",
|
||||||
|
"bower_components"
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,85 @@
|
||||||
|
// 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.Globalization;
|
||||||
|
using System.Net;
|
||||||
|
using System.Security.Principal;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using Microsoft.AspNet.Builder;
|
||||||
|
using Microsoft.AspNet.Http;
|
||||||
|
using Microsoft.Framework.Internal;
|
||||||
|
using Microsoft.Framework.Primitives;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNet.IISPlatformHandler
|
||||||
|
{
|
||||||
|
public class IISPlatformHandlerMiddleware
|
||||||
|
{
|
||||||
|
private const string XForwardedForHeaderName = "X-Forwarded-For";
|
||||||
|
private const string XForwardedProtoHeaderName = "X-Forwarded-Proto";
|
||||||
|
private const string XIISWindowsAuthToken = "X-IIS-WindowsAuthToken";
|
||||||
|
private const string XOriginalProtoName = "X-Original-Proto";
|
||||||
|
private const string XOriginalIPName = "X-Original-IP";
|
||||||
|
|
||||||
|
private readonly RequestDelegate _next;
|
||||||
|
|
||||||
|
public IISPlatformHandlerMiddleware(RequestDelegate next)
|
||||||
|
{
|
||||||
|
_next = next;
|
||||||
|
}
|
||||||
|
|
||||||
|
public Task Invoke(HttpContext httpContext)
|
||||||
|
{
|
||||||
|
var xForwardProtoHeaderValue = httpContext.Request.Headers[XForwardedProtoHeaderName];
|
||||||
|
if (!string.IsNullOrEmpty(xForwardProtoHeaderValue))
|
||||||
|
{
|
||||||
|
if (!string.IsNullOrEmpty(httpContext.Request.Scheme))
|
||||||
|
{
|
||||||
|
httpContext.Request.Headers[XOriginalProtoName] = httpContext.Request.Scheme;
|
||||||
|
}
|
||||||
|
httpContext.Request.Scheme = xForwardProtoHeaderValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
var xForwardedForHeaderValue = httpContext.Request.Headers.GetCommaSeparatedValues(XForwardedForHeaderName);
|
||||||
|
if (xForwardedForHeaderValue != null && xForwardedForHeaderValue.Length > 0)
|
||||||
|
{
|
||||||
|
IPAddress ipFromHeader;
|
||||||
|
if (IPAddress.TryParse(xForwardedForHeaderValue[0], out ipFromHeader))
|
||||||
|
{
|
||||||
|
var remoteIPString = httpContext.Connection.RemoteIpAddress?.ToString();
|
||||||
|
if (!string.IsNullOrEmpty(remoteIPString))
|
||||||
|
{
|
||||||
|
httpContext.Request.Headers[XOriginalIPName] = remoteIPString;
|
||||||
|
}
|
||||||
|
httpContext.Connection.RemoteIpAddress = ipFromHeader;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
var xIISWindowsAuthToken = httpContext.Request.Headers[XIISWindowsAuthToken];
|
||||||
|
int hexHandle;
|
||||||
|
if (!StringValues.IsNullOrEmpty(xIISWindowsAuthToken)
|
||||||
|
&& int.TryParse(xIISWindowsAuthToken, NumberStyles.HexNumber, CultureInfo.InvariantCulture, out hexHandle))
|
||||||
|
{
|
||||||
|
var handle = new IntPtr(hexHandle);
|
||||||
|
var winIdentity = new WindowsIdentity(handle);
|
||||||
|
// WindowsIdentity just duplicated the handle so we need to close the original.
|
||||||
|
NativeMethods.CloseHandle(handle);
|
||||||
|
|
||||||
|
httpContext.Response.RegisterForDispose(winIdentity);
|
||||||
|
var winPrincipal = new WindowsPrincipal(winIdentity);
|
||||||
|
|
||||||
|
var existingPrincipal = httpContext.User;
|
||||||
|
if (existingPrincipal != null)
|
||||||
|
{
|
||||||
|
httpContext.User = SecurityHelper.MergeUserPrincipal(existingPrincipal, winPrincipal);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
httpContext.User = winPrincipal;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return _next(httpContext);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,21 @@
|
||||||
|
// 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 Microsoft.AspNet.IISPlatformHandler;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNet.Builder
|
||||||
|
{
|
||||||
|
public static class IISPlatformHandlerMiddlewareExtensions
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Adds middleware for interacting with the IIS HttpPlatformHandler reverse proxy module.
|
||||||
|
/// This will handle forwarded Windows Authentication, request scheme, remote IPs, etc..
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="builder"></param>
|
||||||
|
/// <returns></returns>
|
||||||
|
public static IApplicationBuilder UseIISPlatformHandler(this IApplicationBuilder builder)
|
||||||
|
{
|
||||||
|
return builder.UseMiddleware<IISPlatformHandlerMiddleware>();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,20 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<Project ToolsVersion="14.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||||
|
<PropertyGroup>
|
||||||
|
<VisualStudioVersion Condition="'$(VisualStudioVersion)' == ''">14.0</VisualStudioVersion>
|
||||||
|
<VSToolsPath Condition="'$(VSToolsPath)' == ''">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)</VSToolsPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.Props" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
<PropertyGroup Label="Globals">
|
||||||
|
<ProjectGuid>abe53415-83ce-4af0-af67-e52160c7862b</ProjectGuid>
|
||||||
|
<RootNamespace>Microsoft.AspNet.PlatformHandler</RootNamespace>
|
||||||
|
<BaseIntermediateOutputPath Condition="'$(BaseIntermediateOutputPath)'=='' ">..\..\artifacts\obj\$(MSBuildProjectName)</BaseIntermediateOutputPath>
|
||||||
|
<OutputPath Condition="'$(OutputPath)'=='' ">..\..\artifacts\bin\$(MSBuildProjectName)\</OutputPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
|
||||||
|
<PropertyGroup>
|
||||||
|
<SchemaVersion>2.0</SchemaVersion>
|
||||||
|
</PropertyGroup>
|
||||||
|
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.targets" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
</Project>
|
||||||
|
|
@ -0,0 +1,24 @@
|
||||||
|
// 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.Runtime.InteropServices;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNet.IISPlatformHandler
|
||||||
|
{
|
||||||
|
internal class NativeMethods
|
||||||
|
{
|
||||||
|
#if DNXCORE50
|
||||||
|
private const string api_ms_win_core_handle_LIB = "api-ms-win-core-handle-l1-1-0.dll";
|
||||||
|
#else
|
||||||
|
private const string KERNEL32 = "kernel32.dll";
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#if DNXCORE50
|
||||||
|
[DllImport(api_ms_win_core_handle_LIB, ExactSpelling = true, SetLastError = true)]
|
||||||
|
#else
|
||||||
|
[DllImport(KERNEL32, ExactSpelling = true, SetLastError = true)]
|
||||||
|
#endif
|
||||||
|
internal static extern bool CloseHandle(IntPtr handle);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,23 @@
|
||||||
|
{
|
||||||
|
"version": "1.0.0-*",
|
||||||
|
"description": "ASP.NET 5 components for working with the IIS HttpPlatformHandler module.",
|
||||||
|
"repository": {
|
||||||
|
"type": "git",
|
||||||
|
"url": "git://github.com/aspnet/IISIntegration"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"Microsoft.AspNet.Http.Extensions": "1.0.0-*",
|
||||||
|
"Microsoft.Framework.SecurityHelper.Sources": {
|
||||||
|
"type": "build",
|
||||||
|
"version": "1.0.0-*"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"frameworks": {
|
||||||
|
"dnx451": { },
|
||||||
|
"dnxcore50": {
|
||||||
|
"dependencies": {
|
||||||
|
"System.Security.Principal.Windows": "4.0.0-beta-*"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,97 @@
|
||||||
|
// 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.IO;
|
||||||
|
using System.Net.Http;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using Microsoft.AspNet.Server.Testing;
|
||||||
|
using Microsoft.AspNet.Testing.xunit;
|
||||||
|
using Microsoft.Framework.Logging;
|
||||||
|
using Xunit;
|
||||||
|
using Xunit.Sdk;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNet.IISPlatformHandler.FunctionalTests
|
||||||
|
{
|
||||||
|
// Uses ports ranging 5061 - 5069.
|
||||||
|
public class HelloWorldTests
|
||||||
|
{
|
||||||
|
[ConditionalTheory]
|
||||||
|
[OSSkipCondition(OperatingSystems.Linux | OperatingSystems.MacOSX)]
|
||||||
|
[InlineData(RuntimeFlavor.Clr, RuntimeArchitecture.x86, "http://localhost:5061/", ServerType.Kestrel)]
|
||||||
|
[InlineData(RuntimeFlavor.Clr, RuntimeArchitecture.x64, "http://localhost:5062/", ServerType.Kestrel)]
|
||||||
|
[InlineData(RuntimeFlavor.CoreClr, RuntimeArchitecture.x86, "http://localhost:5063/", ServerType.Kestrel)]
|
||||||
|
[InlineData(RuntimeFlavor.CoreClr, RuntimeArchitecture.x64, "http://localhost:5064/", ServerType.Kestrel)]
|
||||||
|
public Task HelloWorld_IISExpress(RuntimeFlavor runtimeFlavor, RuntimeArchitecture architecture, string applicationBaseUrl, ServerType delegateServer)
|
||||||
|
{
|
||||||
|
return HelloWorld(ServerType.IISExpress, runtimeFlavor, architecture, applicationBaseUrl, delegateServer);
|
||||||
|
}
|
||||||
|
|
||||||
|
[ConditionalTheory]
|
||||||
|
[OSSkipCondition(OperatingSystems.Linux | OperatingSystems.MacOSX)]
|
||||||
|
[InlineData(RuntimeFlavor.Clr, RuntimeArchitecture.x86, "http://localhost:5065/", ServerType.Kestrel)]
|
||||||
|
[InlineData(RuntimeFlavor.Clr, RuntimeArchitecture.x64, "http://localhost:5066/", ServerType.Kestrel)]
|
||||||
|
[InlineData(RuntimeFlavor.CoreClr, RuntimeArchitecture.x86, "http://localhost:5067/", ServerType.Kestrel)]
|
||||||
|
[InlineData(RuntimeFlavor.CoreClr, RuntimeArchitecture.x64, "http://localhost:5068/", ServerType.Kestrel)]
|
||||||
|
public Task HelloWorld_IISExpress_NoSource(RuntimeFlavor runtimeFlavor, RuntimeArchitecture architecture, string applicationBaseUrl, ServerType delegateServer)
|
||||||
|
{
|
||||||
|
return HelloWorld(ServerType.IISExpress, runtimeFlavor, architecture, applicationBaseUrl, delegateServer, noSource: true);
|
||||||
|
}
|
||||||
|
|
||||||
|
[ConditionalTheory]
|
||||||
|
[SkipIfIISVariationsNotEnabled]
|
||||||
|
[OSSkipCondition(OperatingSystems.MacOSX | OperatingSystems.Linux)]
|
||||||
|
[SkipIfCurrentRuntimeIsCoreClr]
|
||||||
|
[InlineData(RuntimeFlavor.Clr, RuntimeArchitecture.x64, "http://localhost:5069/", ServerType.Kestrel)]
|
||||||
|
[InlineData(RuntimeFlavor.CoreClr, RuntimeArchitecture.x86, "http://localhost:5070/", ServerType.Kestrel)]
|
||||||
|
public Task HelloWorld_IIS(RuntimeFlavor runtimeFlavor, RuntimeArchitecture architecture, string applicationBaseUrl, ServerType delegateServer)
|
||||||
|
{
|
||||||
|
return HelloWorld(ServerType.IIS, runtimeFlavor, architecture, applicationBaseUrl, delegateServer);
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task HelloWorld(ServerType serverType, RuntimeFlavor runtimeFlavor, RuntimeArchitecture architecture, string applicationBaseUrl, ServerType delegateServer, bool noSource = false)
|
||||||
|
{
|
||||||
|
var logger = new LoggerFactory()
|
||||||
|
.AddConsole()
|
||||||
|
.CreateLogger($"HelloWorld:{serverType}:{runtimeFlavor}:{architecture}:{delegateServer}");
|
||||||
|
|
||||||
|
using (logger.BeginScope("HelloWorldTest"))
|
||||||
|
{
|
||||||
|
var deploymentParameters = new DeploymentParameters(Helpers.GetTestSitesPath(), serverType, runtimeFlavor, architecture)
|
||||||
|
{
|
||||||
|
ApplicationBaseUriHint = applicationBaseUrl,
|
||||||
|
Command = delegateServer == ServerType.WebListener ? "web" : "kestrel",
|
||||||
|
PublishWithNoSource = noSource,
|
||||||
|
EnvironmentName = "HelloWorld", // Will pick the Start class named 'StartupHelloWorld',
|
||||||
|
ApplicationHostConfigTemplateContent = (serverType == ServerType.IISExpress) ? File.ReadAllText("Http.config") : null,
|
||||||
|
SiteName = "HttpTestSite", // This is configured in the Http.config
|
||||||
|
};
|
||||||
|
|
||||||
|
using (var deployer = ApplicationDeployerFactory.Create(deploymentParameters, logger))
|
||||||
|
{
|
||||||
|
var deploymentResult = deployer.Deploy();
|
||||||
|
var httpClientHandler = new HttpClientHandler();
|
||||||
|
var httpClient = new HttpClient(httpClientHandler) { BaseAddress = new Uri(deploymentResult.ApplicationBaseUri) };
|
||||||
|
|
||||||
|
// Request to base address and check if various parts of the body are rendered & measure the cold startup time.
|
||||||
|
var response = await RetryHelper.RetryRequest(() =>
|
||||||
|
{
|
||||||
|
return httpClient.GetAsync(string.Empty);
|
||||||
|
}, logger, deploymentResult.HostShutdownToken);
|
||||||
|
|
||||||
|
var responseText = await response.Content.ReadAsStringAsync();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Assert.Equal("Hello World", responseText);
|
||||||
|
}
|
||||||
|
catch (XunitException)
|
||||||
|
{
|
||||||
|
logger.LogWarning(response.ToString());
|
||||||
|
logger.LogWarning(responseText);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,15 @@
|
||||||
|
// 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.IO;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNet.IISPlatformHandler.FunctionalTests
|
||||||
|
{
|
||||||
|
public class Helpers
|
||||||
|
{
|
||||||
|
public static string GetTestSitesPath()
|
||||||
|
{
|
||||||
|
return Path.GetFullPath(Path.Combine("..", "TestSites"));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
|
@ -0,0 +1,186 @@
|
||||||
|
// 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.IO;
|
||||||
|
using System.Net.Http;
|
||||||
|
using System.Security.Cryptography.X509Certificates;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using Microsoft.AspNet.Server.Testing;
|
||||||
|
using Microsoft.AspNet.Testing.xunit;
|
||||||
|
using Microsoft.Framework.Logging;
|
||||||
|
using Xunit;
|
||||||
|
using Xunit.Sdk;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNet.IISPlatformHandler.FunctionalTests
|
||||||
|
{
|
||||||
|
// IisExpress preregisteres 44300-44399 ports.
|
||||||
|
public class HttpsTest
|
||||||
|
{
|
||||||
|
[ConditionalTheory]
|
||||||
|
[OSSkipCondition(OperatingSystems.MacOSX | OperatingSystems.Linux)]
|
||||||
|
[InlineData(RuntimeFlavor.CoreClr, RuntimeArchitecture.x86, "https://localhost:44399/")]
|
||||||
|
[InlineData(RuntimeFlavor.Clr, RuntimeArchitecture.x64, "https://localhost:44398/")]
|
||||||
|
public Task Https_HelloWorld(RuntimeFlavor runtimeFlavor, RuntimeArchitecture architecture, string applicationBaseUrl)
|
||||||
|
{
|
||||||
|
return HttpsHelloWorld(ServerType.IISExpress, runtimeFlavor, architecture, applicationBaseUrl);
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task HttpsHelloWorld(ServerType serverType, RuntimeFlavor runtimeFlavor, RuntimeArchitecture architecture, string applicationBaseUrl)
|
||||||
|
{
|
||||||
|
var logger = new LoggerFactory()
|
||||||
|
.AddConsole()
|
||||||
|
.CreateLogger($"HttpsHelloWorld:{serverType}:{runtimeFlavor}:{architecture}");
|
||||||
|
|
||||||
|
using (logger.BeginScope("HttpsHelloWorldTest"))
|
||||||
|
{
|
||||||
|
var deploymentParameters = new DeploymentParameters(Helpers.GetTestSitesPath(), serverType, runtimeFlavor, architecture)
|
||||||
|
{
|
||||||
|
ApplicationBaseUriHint = applicationBaseUrl,
|
||||||
|
EnvironmentName = "HttpsHelloWorld", // Will pick the Start class named 'StartupHttpsHelloWorld',
|
||||||
|
ApplicationHostConfigTemplateContent = (serverType == ServerType.IISExpress) ? File.ReadAllText("Https.config") : null,
|
||||||
|
SiteName = "HttpsTestSite", // This is configured in the Https.config
|
||||||
|
};
|
||||||
|
|
||||||
|
using (var deployer = ApplicationDeployerFactory.Create(deploymentParameters, logger))
|
||||||
|
{
|
||||||
|
var deploymentResult = deployer.Deploy();
|
||||||
|
var handler = new WebRequestHandler();
|
||||||
|
handler.ServerCertificateValidationCallback = (a, b, c, d) => true;
|
||||||
|
var httpClient = new HttpClient(handler) { BaseAddress = new Uri(deploymentResult.ApplicationBaseUri) };
|
||||||
|
|
||||||
|
// Request to base address and check if various parts of the body are rendered & measure the cold startup time.
|
||||||
|
var response = await RetryHelper.RetryRequest(() =>
|
||||||
|
{
|
||||||
|
return httpClient.GetAsync(string.Empty);
|
||||||
|
}, logger, deploymentResult.HostShutdownToken);
|
||||||
|
|
||||||
|
var responseText = await response.Content.ReadAsStringAsync();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
Assert.Equal("https Hello World", responseText);
|
||||||
|
}
|
||||||
|
catch (XunitException)
|
||||||
|
{
|
||||||
|
logger.LogWarning(response.ToString());
|
||||||
|
logger.LogWarning(responseText);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
[ConditionalTheory]
|
||||||
|
[OSSkipCondition(OperatingSystems.MacOSX | OperatingSystems.Linux)]
|
||||||
|
[InlineData(RuntimeFlavor.CoreClr, RuntimeArchitecture.x64, "https://localhost:44397/")]
|
||||||
|
[InlineData(RuntimeFlavor.Clr, RuntimeArchitecture.x86, "https://localhost:44396/")]
|
||||||
|
public Task Https_HelloWorld_NoClientCert(RuntimeFlavor runtimeFlavor, RuntimeArchitecture architecture, string applicationBaseUrl)
|
||||||
|
{
|
||||||
|
return HttpsHelloWorldCerts(ServerType.IISExpress, runtimeFlavor, architecture, applicationBaseUrl, sendClientCert: false);
|
||||||
|
}
|
||||||
|
|
||||||
|
[ConditionalTheory(Skip = "Manual test only, selecting a client cert is non-determanistic on different machines.")]
|
||||||
|
[OSSkipCondition(OperatingSystems.MacOSX | OperatingSystems.Linux)]
|
||||||
|
[InlineData(RuntimeFlavor.CoreClr, RuntimeArchitecture.x86, "https://localhost:44395/")]
|
||||||
|
[InlineData(RuntimeFlavor.Clr, RuntimeArchitecture.x64, "https://localhost:44394/")]
|
||||||
|
public Task Https_HelloWorld_ClientCert(RuntimeFlavor runtimeFlavor, RuntimeArchitecture architecture, string applicationBaseUrl)
|
||||||
|
{
|
||||||
|
return HttpsHelloWorldCerts(ServerType.IISExpress, runtimeFlavor, architecture, applicationBaseUrl, sendClientCert: true);
|
||||||
|
}
|
||||||
|
|
||||||
|
public async Task HttpsHelloWorldCerts(ServerType serverType, RuntimeFlavor runtimeFlavor, RuntimeArchitecture architecture, string applicationBaseUrl, bool sendClientCert)
|
||||||
|
{
|
||||||
|
var logger = new LoggerFactory()
|
||||||
|
.AddConsole()
|
||||||
|
.CreateLogger($"HttpsHelloWorldCerts:{serverType}:{runtimeFlavor}:{architecture}");
|
||||||
|
|
||||||
|
using (logger.BeginScope("HttpsHelloWorldTest"))
|
||||||
|
{
|
||||||
|
var deploymentParameters = new DeploymentParameters(Helpers.GetTestSitesPath(), serverType, runtimeFlavor, architecture)
|
||||||
|
{
|
||||||
|
ApplicationBaseUriHint = applicationBaseUrl,
|
||||||
|
EnvironmentName = "HttpsHelloWorld", // Will pick the Start class named 'StartupHttpsHelloWorld',
|
||||||
|
ApplicationHostConfigTemplateContent = (serverType == ServerType.IISExpress) ? File.ReadAllText("Https.config") : null,
|
||||||
|
SiteName = "HttpsTestSite", // This is configured in the Https.config
|
||||||
|
};
|
||||||
|
|
||||||
|
using (var deployer = ApplicationDeployerFactory.Create(deploymentParameters, logger))
|
||||||
|
{
|
||||||
|
var deploymentResult = deployer.Deploy();
|
||||||
|
var handler = new WebRequestHandler();
|
||||||
|
handler.ServerCertificateValidationCallback = (a, b, c, d) => true;
|
||||||
|
handler.ClientCertificateOptions = ClientCertificateOption.Manual;
|
||||||
|
if (sendClientCert)
|
||||||
|
{
|
||||||
|
X509Certificate2 clientCert = FindClientCert();
|
||||||
|
Assert.NotNull(clientCert);
|
||||||
|
handler.ClientCertificates.Add(clientCert);
|
||||||
|
}
|
||||||
|
var httpClient = new HttpClient(handler) { BaseAddress = new Uri(deploymentResult.ApplicationBaseUri) };
|
||||||
|
|
||||||
|
// Request to base address and check if various parts of the body are rendered & measure the cold startup time.
|
||||||
|
var response = await RetryHelper.RetryRequest(() =>
|
||||||
|
{
|
||||||
|
return httpClient.GetAsync("checkclientcert");
|
||||||
|
}, logger, deploymentResult.HostShutdownToken);
|
||||||
|
|
||||||
|
var responseText = await response.Content.ReadAsStringAsync();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (sendClientCert)
|
||||||
|
{
|
||||||
|
Assert.Equal("https Hello World, has cert? True", responseText);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
Assert.Equal("https Hello World, has cert? False", responseText);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (XunitException)
|
||||||
|
{
|
||||||
|
logger.LogWarning(response.ToString());
|
||||||
|
logger.LogWarning(responseText);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private X509Certificate2 FindClientCert()
|
||||||
|
{
|
||||||
|
var store = new X509Store();
|
||||||
|
store.Open(OpenFlags.ReadOnly);
|
||||||
|
|
||||||
|
foreach (var cert in store.Certificates)
|
||||||
|
{
|
||||||
|
bool isClientAuth = false;
|
||||||
|
bool isSmartCard = false;
|
||||||
|
foreach (var extension in cert.Extensions)
|
||||||
|
{
|
||||||
|
var eku = extension as X509EnhancedKeyUsageExtension;
|
||||||
|
if (eku != null)
|
||||||
|
{
|
||||||
|
foreach (var oid in eku.EnhancedKeyUsages)
|
||||||
|
{
|
||||||
|
if (oid.FriendlyName == "Client Authentication")
|
||||||
|
{
|
||||||
|
isClientAuth = true;
|
||||||
|
}
|
||||||
|
else if (oid.FriendlyName == "Smart Card Logon")
|
||||||
|
{
|
||||||
|
isSmartCard = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isClientAuth && !isSmartCard)
|
||||||
|
{
|
||||||
|
return cert;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,21 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<Project ToolsVersion="14.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||||
|
<PropertyGroup>
|
||||||
|
<VisualStudioVersion Condition="'$(VisualStudioVersion)' == ''">14.0</VisualStudioVersion>
|
||||||
|
<VSToolsPath Condition="'$(VSToolsPath)' == ''">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)</VSToolsPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.Props" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
<PropertyGroup Label="Globals">
|
||||||
|
<ProjectGuid>a83a33d1-3d29-403c-9750-5811ac7b4025</ProjectGuid>
|
||||||
|
<RootNamespace>Microsoft.AspNet.PlatformHandler.FunctionalTests</RootNamespace>
|
||||||
|
<BaseIntermediateOutputPath Condition="'$(BaseIntermediateOutputPath)'=='' ">..\..\artifacts\obj\$(MSBuildProjectName)</BaseIntermediateOutputPath>
|
||||||
|
<OutputPath Condition="'$(OutputPath)'=='' ">..\..\artifacts\bin\$(MSBuildProjectName)\</OutputPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
<PropertyGroup>
|
||||||
|
<SchemaVersion>2.0</SchemaVersion>
|
||||||
|
</PropertyGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<Service Include="{82a7f48d-3b50-4b1e-b82e-3ada8210c358}" />
|
||||||
|
</ItemGroup>
|
||||||
|
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.targets" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
</Project>
|
||||||
File diff suppressed because it is too large
Load Diff
|
|
@ -0,0 +1,115 @@
|
||||||
|
// 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.IO;
|
||||||
|
using System.Net;
|
||||||
|
using System.Net.Http;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using Microsoft.AspNet.Server.Testing;
|
||||||
|
using Microsoft.AspNet.Testing.xunit;
|
||||||
|
using Microsoft.Framework.Logging;
|
||||||
|
using Xunit;
|
||||||
|
using Xunit.Sdk;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNet.IISPlatformHandler.FunctionalTests
|
||||||
|
{
|
||||||
|
// Uses ports ranging 5050 - 5060.
|
||||||
|
public class NtlmAuthenticationTests
|
||||||
|
{
|
||||||
|
// TODO: The middleware needs to implement auth handlers.
|
||||||
|
[ConditionalTheory, Trait("ServerComparison.FunctionalTests", "ServerComparison.FunctionalTests")]
|
||||||
|
[OSSkipCondition(OperatingSystems.Linux | OperatingSystems.MacOSX)]
|
||||||
|
[InlineData(ServerType.IISExpress, RuntimeFlavor.CoreClr, RuntimeArchitecture.x86, "http://localhost:5050/")]
|
||||||
|
[InlineData(ServerType.IISExpress, RuntimeFlavor.Clr, RuntimeArchitecture.x64, "http://localhost:5051/")]
|
||||||
|
public async Task NtlmAuthentication(ServerType serverType, RuntimeFlavor runtimeFlavor, RuntimeArchitecture architecture, string applicationBaseUrl)
|
||||||
|
{
|
||||||
|
var logger = new LoggerFactory()
|
||||||
|
.AddConsole()
|
||||||
|
.CreateLogger($"HttpsHelloWorld:{serverType}:{runtimeFlavor}:{architecture}");
|
||||||
|
|
||||||
|
using (logger.BeginScope("NtlmAuthenticationTest"))
|
||||||
|
{
|
||||||
|
var deploymentParameters = new DeploymentParameters(Helpers.GetTestSitesPath(), serverType, runtimeFlavor, architecture)
|
||||||
|
{
|
||||||
|
ApplicationBaseUriHint = applicationBaseUrl,
|
||||||
|
EnvironmentName = "NtlmAuthentication", // Will pick the Start class named 'StartupNtlmAuthentication'
|
||||||
|
ApplicationHostConfigTemplateContent = (serverType == ServerType.IISExpress) ? File.ReadAllText("NtlmAuthentation.config") : null,
|
||||||
|
SiteName = "NtlmAuthenticationTestSite", // This is configured in the NtlmAuthentication.config
|
||||||
|
};
|
||||||
|
|
||||||
|
using (var deployer = ApplicationDeployerFactory.Create(deploymentParameters, logger))
|
||||||
|
{
|
||||||
|
var deploymentResult = deployer.Deploy();
|
||||||
|
var httpClientHandler = new HttpClientHandler();
|
||||||
|
var httpClient = new HttpClient(httpClientHandler) { BaseAddress = new Uri(deploymentResult.ApplicationBaseUri) };
|
||||||
|
|
||||||
|
// Request to base address and check if various parts of the body are rendered & measure the cold startup time.
|
||||||
|
var response = await RetryHelper.RetryRequest(() =>
|
||||||
|
{
|
||||||
|
return httpClient.GetAsync(string.Empty);
|
||||||
|
}, logger, deploymentResult.HostShutdownToken);
|
||||||
|
|
||||||
|
var responseText = await response.Content.ReadAsStringAsync();
|
||||||
|
try
|
||||||
|
{
|
||||||
|
// TODO: Currently we do not implement mixed auth.
|
||||||
|
// https://github.com/aspnet/IISIntegration/issues/1
|
||||||
|
Assert.Equal(HttpStatusCode.Unauthorized, response.StatusCode);
|
||||||
|
Assert.Contains("NTLM", response.Headers.WwwAuthenticate.ToString());
|
||||||
|
Assert.Contains("Negotiate", response.Headers.WwwAuthenticate.ToString());
|
||||||
|
|
||||||
|
/*
|
||||||
|
Assert.Equal("Hello World", responseText);
|
||||||
|
|
||||||
|
responseText = await httpClient.GetStringAsync("/Anonymous");
|
||||||
|
Assert.Equal("Anonymous?True", responseText);
|
||||||
|
|
||||||
|
response = await httpClient.GetAsync("/Restricted");
|
||||||
|
Assert.Equal(HttpStatusCode.Unauthorized, response.StatusCode);
|
||||||
|
Assert.Contains("NTLM", response.Headers.WwwAuthenticate.ToString());
|
||||||
|
Assert.Contains("Negotiate", response.Headers.WwwAuthenticate.ToString());
|
||||||
|
|
||||||
|
response = await httpClient.GetAsync("/RestrictedNTLM");
|
||||||
|
Assert.Equal(HttpStatusCode.Unauthorized, response.StatusCode);
|
||||||
|
Assert.Contains("NTLM", response.Headers.WwwAuthenticate.ToString());
|
||||||
|
// Note we can't restrict a challenge to a specific auth type, the native auth modules always add themselves.
|
||||||
|
Assert.Contains("Negotiate", response.Headers.WwwAuthenticate.ToString());
|
||||||
|
|
||||||
|
response = await httpClient.GetAsync("/Forbidden");
|
||||||
|
Assert.Equal(HttpStatusCode.Forbidden, response.StatusCode);
|
||||||
|
*/
|
||||||
|
httpClientHandler = new HttpClientHandler() { UseDefaultCredentials = true };
|
||||||
|
httpClient = new HttpClient(httpClientHandler) { BaseAddress = new Uri(deploymentResult.ApplicationBaseUri) };
|
||||||
|
|
||||||
|
responseText = await httpClient.GetStringAsync("/Anonymous");
|
||||||
|
Assert.Equal("Anonymous?False", responseText);
|
||||||
|
|
||||||
|
/*
|
||||||
|
response = await httpClient.GetAsync("/AutoForbid");
|
||||||
|
Assert.Equal(HttpStatusCode.Forbidden, response.StatusCode);
|
||||||
|
|
||||||
|
responseText = await httpClient.GetStringAsync("/Restricted");
|
||||||
|
Assert.Equal("Negotiate", responseText);
|
||||||
|
|
||||||
|
responseText = await httpClient.GetStringAsync("/RestrictedNegotiate");
|
||||||
|
Assert.Equal("Negotiate", responseText);
|
||||||
|
|
||||||
|
response = await httpClient.GetAsync("/RestrictedNTLM");
|
||||||
|
// This isn't a Forbidden because we authenticate with Negotiate and challenge for NTLM.
|
||||||
|
// Note we can't restrict a challenge to a specific auth type, the native auth modules always add themselves,
|
||||||
|
// so both Negotiate and NTLM get sent again.
|
||||||
|
Assert.Equal(HttpStatusCode.Unauthorized, response.StatusCode);
|
||||||
|
*/
|
||||||
|
}
|
||||||
|
catch (XunitException)
|
||||||
|
{
|
||||||
|
logger.LogWarning(response.ToString());
|
||||||
|
logger.LogWarning(responseText);
|
||||||
|
throw;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,3 @@
|
||||||
|
using Xunit;
|
||||||
|
|
||||||
|
[assembly: CollectionBehavior(CollectionBehavior.CollectionPerAssembly)]
|
||||||
|
|
@ -0,0 +1,23 @@
|
||||||
|
{
|
||||||
|
"compilationOptions": {
|
||||||
|
"warningsAsErrors": true
|
||||||
|
},
|
||||||
|
"commands": {
|
||||||
|
"test": "xunit.runner.aspnet"
|
||||||
|
},
|
||||||
|
"dependencies": {
|
||||||
|
"Microsoft.AspNet.Server.Testing": "1.0.0-*",
|
||||||
|
"Microsoft.Framework.Logging.Console": "1.0.0-*",
|
||||||
|
"xunit.runner.aspnet": "2.0.0-aspnet-*"
|
||||||
|
},
|
||||||
|
"frameworks": {
|
||||||
|
"dnx451": {
|
||||||
|
"frameworkAssemblies": {
|
||||||
|
"System.Data": "",
|
||||||
|
"System.Net.Http": "",
|
||||||
|
"System.Net.Http.WebRequest": "",
|
||||||
|
"System.Xml": ""
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,80 @@
|
||||||
|
// 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.Net.Http;
|
||||||
|
using System.Threading.Tasks;
|
||||||
|
using Microsoft.AspNet.Builder;
|
||||||
|
using Microsoft.AspNet.TestHost;
|
||||||
|
using Xunit;
|
||||||
|
|
||||||
|
namespace Microsoft.AspNet.IISPlatformHandler
|
||||||
|
{
|
||||||
|
public class HttpPlatformHandlerMiddlewareTests
|
||||||
|
{
|
||||||
|
[Fact]
|
||||||
|
public async Task XForwardedForOverrideChangesRemoteIp()
|
||||||
|
{
|
||||||
|
var assertsExecuted = false;
|
||||||
|
|
||||||
|
var server = TestServer.Create(app =>
|
||||||
|
{
|
||||||
|
app.UseIISPlatformHandler();
|
||||||
|
app.Run(context =>
|
||||||
|
{
|
||||||
|
Assert.Equal("11.111.111.11", context.Connection.RemoteIpAddress.ToString());
|
||||||
|
assertsExecuted = true;
|
||||||
|
return Task.FromResult(0);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
var req = new HttpRequestMessage(HttpMethod.Get, "");
|
||||||
|
req.Headers.Add("X-Forwarded-For", "11.111.111.11");
|
||||||
|
await server.CreateClient().SendAsync(req);
|
||||||
|
Assert.True(assertsExecuted);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task XForwardedForOverrideBadIpDoesntChangeRemoteIp()
|
||||||
|
{
|
||||||
|
var assertsExecuted = false;
|
||||||
|
|
||||||
|
var server = TestServer.Create(app =>
|
||||||
|
{
|
||||||
|
app.UseIISPlatformHandler();
|
||||||
|
app.Run(context =>
|
||||||
|
{
|
||||||
|
Assert.Null(context.Connection.RemoteIpAddress);
|
||||||
|
assertsExecuted = true;
|
||||||
|
return Task.FromResult(0);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
var req = new HttpRequestMessage(HttpMethod.Get, "");
|
||||||
|
req.Headers.Add("X-Forwarded-For", "BAD-IP");
|
||||||
|
await server.CreateClient().SendAsync(req);
|
||||||
|
Assert.True(assertsExecuted);
|
||||||
|
}
|
||||||
|
|
||||||
|
[Fact]
|
||||||
|
public async Task XForwardedProtoOverrideChangesRequestProtocol()
|
||||||
|
{
|
||||||
|
var assertsExecuted = false;
|
||||||
|
|
||||||
|
var server = TestServer.Create(app =>
|
||||||
|
{
|
||||||
|
app.UseIISPlatformHandler();
|
||||||
|
app.Run(context =>
|
||||||
|
{
|
||||||
|
Assert.Equal("TestProtocol", context.Request.Scheme);
|
||||||
|
assertsExecuted = true;
|
||||||
|
return Task.FromResult(0);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
var req = new HttpRequestMessage(HttpMethod.Get, "");
|
||||||
|
req.Headers.Add("X-Forwarded-Proto", "TestProtocol");
|
||||||
|
await server.CreateClient().SendAsync(req);
|
||||||
|
Assert.True(assertsExecuted);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,21 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<Project ToolsVersion="14.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||||
|
<PropertyGroup>
|
||||||
|
<VisualStudioVersion Condition="'$(VisualStudioVersion)' == ''">14.0</VisualStudioVersion>
|
||||||
|
<VSToolsPath Condition="'$(VSToolsPath)' == ''">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)</VSToolsPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.Props" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
<PropertyGroup Label="Globals">
|
||||||
|
<ProjectGuid>fbbbe015-1ce3-454b-9647-23f8073fb7ab</ProjectGuid>
|
||||||
|
<RootNamespace>Microsoft.AspNet.PipelineHandler.Tests</RootNamespace>
|
||||||
|
<BaseIntermediateOutputPath Condition="'$(BaseIntermediateOutputPath)'=='' ">..\..\artifacts\obj\$(MSBuildProjectName)</BaseIntermediateOutputPath>
|
||||||
|
<OutputPath Condition="'$(OutputPath)'=='' ">..\..\artifacts\bin\$(MSBuildProjectName)\</OutputPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
<PropertyGroup>
|
||||||
|
<SchemaVersion>2.0</SchemaVersion>
|
||||||
|
</PropertyGroup>
|
||||||
|
<ItemGroup>
|
||||||
|
<Service Include="{82a7f48d-3b50-4b1e-b82e-3ada8210c358}" />
|
||||||
|
</ItemGroup>
|
||||||
|
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.targets" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
</Project>
|
||||||
|
|
@ -0,0 +1,15 @@
|
||||||
|
{
|
||||||
|
"version": "1.0.0-*",
|
||||||
|
"dependencies": {
|
||||||
|
"Microsoft.AspNet.IISPlatformHandler": "1.0.0-*",
|
||||||
|
"Microsoft.AspNet.TestHost": "1.0.0-*",
|
||||||
|
"xunit.runner.aspnet": "2.0.0-aspnet-*"
|
||||||
|
},
|
||||||
|
"commands": {
|
||||||
|
"test": "xunit.runner.aspnet"
|
||||||
|
},
|
||||||
|
"frameworks": {
|
||||||
|
"dnx451": { },
|
||||||
|
"dnxcore50": { }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,11 @@
|
||||||
|
{
|
||||||
|
"profiles": {
|
||||||
|
"IIS Express": {
|
||||||
|
"commandName": "IISExpress",
|
||||||
|
"launchBrowser": true,
|
||||||
|
"environmentVariables": {
|
||||||
|
"ASPNET_ENV": "HelloWorld"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,22 @@
|
||||||
|
// 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 Microsoft.AspNet.Builder;
|
||||||
|
using Microsoft.AspNet.Http;
|
||||||
|
using Microsoft.Framework.Logging;
|
||||||
|
|
||||||
|
namespace TestSites
|
||||||
|
{
|
||||||
|
public class StartupHelloWorld
|
||||||
|
{
|
||||||
|
public void Configure(IApplicationBuilder app, ILoggerFactory loggerFactory)
|
||||||
|
{
|
||||||
|
loggerFactory.AddConsole();
|
||||||
|
app.UseIISPlatformHandler();
|
||||||
|
app.Run(ctx =>
|
||||||
|
{
|
||||||
|
return ctx.Response.WriteAsync("Hello World");
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,26 @@
|
||||||
|
// 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 Microsoft.AspNet.Builder;
|
||||||
|
using Microsoft.AspNet.Http;
|
||||||
|
using Microsoft.Framework.Logging;
|
||||||
|
|
||||||
|
namespace TestSites
|
||||||
|
{
|
||||||
|
public class StartupHttpsHelloWorld
|
||||||
|
{
|
||||||
|
public void Configure(IApplicationBuilder app, ILoggerFactory loggerFactory)
|
||||||
|
{
|
||||||
|
loggerFactory.AddConsole();
|
||||||
|
app.UseIISPlatformHandler();
|
||||||
|
app.Run(ctx =>
|
||||||
|
{
|
||||||
|
if (ctx.Request.Path.Equals(new PathString("/checkclientcert")))
|
||||||
|
{
|
||||||
|
return ctx.Response.WriteAsync(ctx.Request.Scheme + " Hello World, has cert? " + (ctx.Connection.ClientCertificate != null));
|
||||||
|
}
|
||||||
|
return ctx.Response.WriteAsync(ctx.Request.Scheme + " Hello World");
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,73 @@
|
||||||
|
// 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 Microsoft.AspNet.Builder;
|
||||||
|
using Microsoft.AspNet.Http;
|
||||||
|
using Microsoft.Framework.Logging;
|
||||||
|
|
||||||
|
namespace TestSites
|
||||||
|
{
|
||||||
|
public class StartupNtlmAuthentication
|
||||||
|
{
|
||||||
|
public void Configure(IApplicationBuilder app, ILoggerFactory loggerFactory)
|
||||||
|
{
|
||||||
|
loggerFactory.AddConsole();
|
||||||
|
app.UseIISPlatformHandler();
|
||||||
|
app.Use((context, next) =>
|
||||||
|
{
|
||||||
|
if (context.Request.Path.Equals("/Anonymous"))
|
||||||
|
{
|
||||||
|
return context.Response.WriteAsync("Anonymous?" + !context.User.Identity.IsAuthenticated);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (context.Request.Path.Equals("/Restricted"))
|
||||||
|
{
|
||||||
|
if (context.User.Identity.IsAuthenticated)
|
||||||
|
{
|
||||||
|
return context.Response.WriteAsync(context.User.Identity.AuthenticationType);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return context.Authentication.ChallengeAsync();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (context.Request.Path.Equals("/Forbidden"))
|
||||||
|
{
|
||||||
|
return context.Authentication.ForbidAsync(string.Empty);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (context.Request.Path.Equals("/AutoForbid"))
|
||||||
|
{
|
||||||
|
return context.Authentication.ChallengeAsync();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (context.Request.Path.Equals("/RestrictedNegotiate"))
|
||||||
|
{
|
||||||
|
if (string.Equals("Negotiate", context.User.Identity.AuthenticationType, System.StringComparison.Ordinal))
|
||||||
|
{
|
||||||
|
return context.Response.WriteAsync("Negotiate");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return context.Authentication.ChallengeAsync("Negotiate");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (context.Request.Path.Equals("/RestrictedNTLM"))
|
||||||
|
{
|
||||||
|
if (string.Equals("NTLM", context.User.Identity.AuthenticationType, System.StringComparison.Ordinal))
|
||||||
|
{
|
||||||
|
return context.Response.WriteAsync("NTLM");
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
return context.Authentication.ChallengeAsync("NTLM");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return context.Response.WriteAsync("Hello World");
|
||||||
|
});
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,19 @@
|
||||||
|
<?xml version="1.0" encoding="utf-8"?>
|
||||||
|
<Project ToolsVersion="14.0" DefaultTargets="Build" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
|
||||||
|
<PropertyGroup>
|
||||||
|
<VisualStudioVersion Condition="'$(VisualStudioVersion)' == ''">14.0</VisualStudioVersion>
|
||||||
|
<VSToolsPath Condition="'$(VSToolsPath)' == ''">$(MSBuildExtensionsPath32)\Microsoft\VisualStudio\v$(VisualStudioVersion)</VSToolsPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.Props" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
<PropertyGroup Label="Globals">
|
||||||
|
<ProjectGuid>e27453ad-9ca0-49a2-94fa-96337d77677d</ProjectGuid>
|
||||||
|
<RootNamespace>Sites</RootNamespace>
|
||||||
|
<BaseIntermediateOutputPath Condition="'$(BaseIntermediateOutputPath)'=='' ">..\..\artifacts\obj\$(MSBuildProjectName)</BaseIntermediateOutputPath>
|
||||||
|
<OutputPath Condition="'$(OutputPath)'=='' ">..\..\artifacts\bin\$(MSBuildProjectName)\</OutputPath>
|
||||||
|
</PropertyGroup>
|
||||||
|
<PropertyGroup>
|
||||||
|
<SchemaVersion>2.0</SchemaVersion>
|
||||||
|
<DevelopmentServerPort>11738</DevelopmentServerPort>
|
||||||
|
</PropertyGroup>
|
||||||
|
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.targets" Condition="'$(VSToolsPath)' != ''" />
|
||||||
|
</Project>
|
||||||
|
|
@ -0,0 +1,39 @@
|
||||||
|
{
|
||||||
|
"webroot": "wwwroot",
|
||||||
|
"version": "1.0.0-*",
|
||||||
|
"dependencies": {
|
||||||
|
"Microsoft.AspNet.IISPlatformHandler": "1.0.0-*",
|
||||||
|
"Microsoft.AspNet.Server.Kestrel": "1.0.0-*",
|
||||||
|
"Microsoft.AspNet.Server.WebListener": "1.0.0-*",
|
||||||
|
"Microsoft.AspNet.WebUtilities": "1.0.0-*",
|
||||||
|
"Microsoft.Framework.Configuration.EnvironmentVariables": "1.0.0-*",
|
||||||
|
"Microsoft.Framework.Configuration.Json": "1.0.0-*",
|
||||||
|
"Microsoft.Framework.Logging.Console": "1.0.0-*",
|
||||||
|
"xunit.runner.aspnet": "2.0.0-aspnet-*"
|
||||||
|
},
|
||||||
|
"frameworks": {
|
||||||
|
"dnx451": { },
|
||||||
|
"dnxcore50": {
|
||||||
|
"dependencies": {
|
||||||
|
"System.Net.Primitives": "4.0.11-beta-*",
|
||||||
|
"System.Runtime": "4.0.21-beta-*"
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
"commands": {
|
||||||
|
"web": "Microsoft.AspNet.Server.WebListener",
|
||||||
|
"kestrel": "Microsoft.AspNet.Server.Kestrel"
|
||||||
|
},
|
||||||
|
"publishExclude": [
|
||||||
|
"node_modules",
|
||||||
|
"bower_components",
|
||||||
|
"**.xproj",
|
||||||
|
"**.user",
|
||||||
|
"**.vspscc"
|
||||||
|
],
|
||||||
|
"exclude": [
|
||||||
|
"wwwroot",
|
||||||
|
"node_modules",
|
||||||
|
"bower_components"
|
||||||
|
]
|
||||||
|
}
|
||||||
Loading…
Reference in New Issue