React to routing cleanup
This commit is contained in:
parent
99f501152b
commit
09a293afe9
17
Mvc.sln
17
Mvc.sln
|
|
@ -1,7 +1,7 @@
|
||||||
|
|
||||||
Microsoft Visual Studio Solution File, Format Version 12.00
|
Microsoft Visual Studio Solution File, Format Version 12.00
|
||||||
# Visual Studio 14
|
# Visual Studio 14
|
||||||
VisualStudioVersion = 14.0.24627.0
|
VisualStudioVersion = 14.0.24711.0
|
||||||
MinimumVisualStudioVersion = 10.0.40219.1
|
MinimumVisualStudioVersion = 10.0.40219.1
|
||||||
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "samples", "samples", "{DAAE4C74-D06F-4874-A166-33305D2643CE}"
|
Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "samples", "samples", "{DAAE4C74-D06F-4874-A166-33305D2643CE}"
|
||||||
EndProject
|
EndProject
|
||||||
|
|
@ -114,8 +114,6 @@ Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "UserClassLibrary", "test\We
|
||||||
EndProject
|
EndProject
|
||||||
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "ControllerDiscoveryConventionsWebSite", "test\WebSites\ControllerDiscoveryConventionsWebSite\ControllerDiscoveryConventionsWebSite.xproj", "{A19022EF-9BA3-4349-94E4-F48E13E1C8AE}"
|
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "ControllerDiscoveryConventionsWebSite", "test\WebSites\ControllerDiscoveryConventionsWebSite\ControllerDiscoveryConventionsWebSite.xproj", "{A19022EF-9BA3-4349-94E4-F48E13E1C8AE}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "BestEffortLinkGenerationWebSite", "test\WebSites\BestEffortLinkGenerationWebSite\BestEffortLinkGenerationWebSite.xproj", "{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}"
|
|
||||||
EndProject
|
|
||||||
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "LowercaseUrlsWebSite", "test\WebSites\LowercaseUrlsWebSite\LowercaseUrlsWebSite.xproj", "{BCDB13A6-7D6E-485E-8424-A156432B71AC}"
|
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "LowercaseUrlsWebSite", "test\WebSites\LowercaseUrlsWebSite\LowercaseUrlsWebSite.xproj", "{BCDB13A6-7D6E-485E-8424-A156432B71AC}"
|
||||||
EndProject
|
EndProject
|
||||||
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "Microsoft.AspNet.Mvc.TestCommon", "test\Microsoft.AspNet.Mvc.TestCommon\Microsoft.AspNet.Mvc.TestCommon.xproj", "{F504357E-C2E1-4818-BA5C-9A2EAC25FEE5}"
|
Project("{8BB2217D-0F2D-49D1-97BC-3654ED321F3B}") = "Microsoft.AspNet.Mvc.TestCommon", "test\Microsoft.AspNet.Mvc.TestCommon\Microsoft.AspNet.Mvc.TestCommon.xproj", "{F504357E-C2E1-4818-BA5C-9A2EAC25FEE5}"
|
||||||
|
|
@ -702,18 +700,6 @@ Global
|
||||||
{A19022EF-9BA3-4349-94E4-F48E13E1C8AE}.Release|Mixed Platforms.Build.0 = Release|Any CPU
|
{A19022EF-9BA3-4349-94E4-F48E13E1C8AE}.Release|Mixed Platforms.Build.0 = Release|Any CPU
|
||||||
{A19022EF-9BA3-4349-94E4-F48E13E1C8AE}.Release|x86.ActiveCfg = Release|Any CPU
|
{A19022EF-9BA3-4349-94E4-F48E13E1C8AE}.Release|x86.ActiveCfg = Release|Any CPU
|
||||||
{A19022EF-9BA3-4349-94E4-F48E13E1C8AE}.Release|x86.Build.0 = Release|Any CPU
|
{A19022EF-9BA3-4349-94E4-F48E13E1C8AE}.Release|x86.Build.0 = Release|Any CPU
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Debug|Mixed Platforms.Build.0 = Debug|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Debug|x86.ActiveCfg = Debug|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Debug|x86.Build.0 = Debug|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Release|Any CPU.Build.0 = Release|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Release|Mixed Platforms.ActiveCfg = Release|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Release|Mixed Platforms.Build.0 = Release|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Release|x86.ActiveCfg = Release|Any CPU
|
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34}.Release|x86.Build.0 = Release|Any CPU
|
|
||||||
{BCDB13A6-7D6E-485E-8424-A156432B71AC}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
{BCDB13A6-7D6E-485E-8424-A156432B71AC}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||||
{BCDB13A6-7D6E-485E-8424-A156432B71AC}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
{BCDB13A6-7D6E-485E-8424-A156432B71AC}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||||
{BCDB13A6-7D6E-485E-8424-A156432B71AC}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
{BCDB13A6-7D6E-485E-8424-A156432B71AC}.Debug|Mixed Platforms.ActiveCfg = Debug|Any CPU
|
||||||
|
|
@ -1092,7 +1078,6 @@ Global
|
||||||
{551DC89E-2A13-4CF2-83D7-1ADD802443D5} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
{551DC89E-2A13-4CF2-83D7-1ADD802443D5} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
||||||
{C651F432-4EBE-41A6-BAD2-3E07CCBA209C} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
{C651F432-4EBE-41A6-BAD2-3E07CCBA209C} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
||||||
{A19022EF-9BA3-4349-94E4-F48E13E1C8AE} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
{A19022EF-9BA3-4349-94E4-F48E13E1C8AE} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
||||||
{B11C99C9-E577-4CA2-AC53-4F20EA71AD34} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
|
||||||
{BCDB13A6-7D6E-485E-8424-A156432B71AC} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
{BCDB13A6-7D6E-485E-8424-A156432B71AC} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
||||||
{F504357E-C2E1-4818-BA5C-9A2EAC25FEE5} = {3BA657BF-28B1-42DA-B5B0-1C4601FCF7B1}
|
{F504357E-C2E1-4818-BA5C-9A2EAC25FEE5} = {3BA657BF-28B1-42DA-B5B0-1C4601FCF7B1}
|
||||||
{94BA134D-04B3-48AA-BA55-5A4DB8640F2D} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
{94BA134D-04B3-48AA-BA55-5A4DB8640F2D} = {16703B76-C9F7-4C75-AE6C-53D92E308E3C}
|
||||||
|
|
|
||||||
|
|
@ -18,18 +18,15 @@ namespace Microsoft.AspNet.Mvc.Infrastructure
|
||||||
{
|
{
|
||||||
public class DefaultActionSelector : IActionSelector
|
public class DefaultActionSelector : IActionSelector
|
||||||
{
|
{
|
||||||
private readonly IActionDescriptorsCollectionProvider _actionDescriptorsCollectionProvider;
|
|
||||||
private readonly IActionSelectorDecisionTreeProvider _decisionTreeProvider;
|
private readonly IActionSelectorDecisionTreeProvider _decisionTreeProvider;
|
||||||
private readonly IActionConstraintProvider[] _actionConstraintProviders;
|
private readonly IActionConstraintProvider[] _actionConstraintProviders;
|
||||||
private ILogger _logger;
|
private ILogger _logger;
|
||||||
|
|
||||||
public DefaultActionSelector(
|
public DefaultActionSelector(
|
||||||
IActionDescriptorsCollectionProvider actionDescriptorsCollectionProvider,
|
|
||||||
IActionSelectorDecisionTreeProvider decisionTreeProvider,
|
IActionSelectorDecisionTreeProvider decisionTreeProvider,
|
||||||
IEnumerable<IActionConstraintProvider> actionConstraintProviders,
|
IEnumerable<IActionConstraintProvider> actionConstraintProviders,
|
||||||
ILoggerFactory loggerFactory)
|
ILoggerFactory loggerFactory)
|
||||||
{
|
{
|
||||||
_actionDescriptorsCollectionProvider = actionDescriptorsCollectionProvider;
|
|
||||||
_decisionTreeProvider = decisionTreeProvider;
|
_decisionTreeProvider = decisionTreeProvider;
|
||||||
_actionConstraintProviders = actionConstraintProviders.OrderBy(item => item.Order).ToArray();
|
_actionConstraintProviders = actionConstraintProviders.OrderBy(item => item.Order).ToArray();
|
||||||
_logger = loggerFactory.CreateLogger<DefaultActionSelector>();
|
_logger = loggerFactory.CreateLogger<DefaultActionSelector>();
|
||||||
|
|
@ -211,30 +208,6 @@ namespace Microsoft.AspNet.Mvc.Infrastructure
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// This method attempts to ensure that the route that's about to generate a link will generate a link
|
|
||||||
// to an existing action. This method is called by a route (through MvcApplication) prior to generating
|
|
||||||
// any link - this gives WebFX a chance to 'veto' the values provided by a route.
|
|
||||||
//
|
|
||||||
// This method does not take httpmethod or dynamic action constraints into account.
|
|
||||||
public virtual bool HasValidAction(VirtualPathContext context)
|
|
||||||
{
|
|
||||||
if (context == null)
|
|
||||||
{
|
|
||||||
throw new ArgumentNullException(nameof(context));
|
|
||||||
}
|
|
||||||
|
|
||||||
if (context.ProvidedValues == null)
|
|
||||||
{
|
|
||||||
// We need the route's values to be able to double check our work.
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
var tree = _decisionTreeProvider.DecisionTree;
|
|
||||||
var matchingRouteConstraints = tree.Select(context.ProvidedValues);
|
|
||||||
|
|
||||||
return matchingRouteConstraints.Count > 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
private IReadOnlyList<IActionConstraint> GetConstraints(HttpContext httpContext, ActionDescriptor action)
|
private IReadOnlyList<IActionConstraint> GetConstraints(HttpContext httpContext, ActionDescriptor action)
|
||||||
{
|
{
|
||||||
if (action.ActionConstraints == null || action.ActionConstraints.Count == 0)
|
if (action.ActionConstraints == null || action.ActionConstraints.Count == 0)
|
||||||
|
|
|
||||||
|
|
@ -10,7 +10,5 @@ namespace Microsoft.AspNet.Mvc.Infrastructure
|
||||||
public interface IActionSelector
|
public interface IActionSelector
|
||||||
{
|
{
|
||||||
Task<ActionDescriptor> SelectAsync(RouteContext context);
|
Task<ActionDescriptor> SelectAsync(RouteContext context);
|
||||||
|
|
||||||
bool HasValidAction(VirtualPathContext context);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -34,8 +34,6 @@ namespace Microsoft.AspNet.Mvc.Infrastructure
|
||||||
throw new ArgumentNullException(nameof(context));
|
throw new ArgumentNullException(nameof(context));
|
||||||
}
|
}
|
||||||
|
|
||||||
context.IsBound = true;
|
|
||||||
|
|
||||||
// We return null here because we're not responsible for generating the url, the route is.
|
// We return null here because we're not responsible for generating the url, the route is.
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
|
||||||
|
|
@ -55,40 +55,6 @@ namespace Microsoft.AspNet.Mvc.Infrastructure
|
||||||
Assert.Equal(expectedMessage, sink.Writes[0].State?.ToString());
|
Assert.Equal(expectedMessage, sink.Writes[0].State?.ToString());
|
||||||
}
|
}
|
||||||
|
|
||||||
[Fact]
|
|
||||||
public void HasValidAction_Match()
|
|
||||||
{
|
|
||||||
// Arrange
|
|
||||||
var actions = GetActions();
|
|
||||||
|
|
||||||
var selector = CreateSelector(actions);
|
|
||||||
var context = CreateContext(new { });
|
|
||||||
context.ProvidedValues = new RouteValueDictionary(new { controller = "Home", action = "Index" });
|
|
||||||
|
|
||||||
// Act
|
|
||||||
var isValid = selector.HasValidAction(context);
|
|
||||||
|
|
||||||
// Assert
|
|
||||||
Assert.True(isValid);
|
|
||||||
}
|
|
||||||
|
|
||||||
[Fact]
|
|
||||||
public void HasValidAction_NoMatch()
|
|
||||||
{
|
|
||||||
// Arrange
|
|
||||||
var actions = GetActions();
|
|
||||||
|
|
||||||
var selector = CreateSelector(actions);
|
|
||||||
var context = CreateContext(new { });
|
|
||||||
context.ProvidedValues = new RouteValueDictionary(new { controller = "Home", action = "FakeAction" });
|
|
||||||
|
|
||||||
// Act
|
|
||||||
var isValid = selector.HasValidAction(context);
|
|
||||||
|
|
||||||
// Assert
|
|
||||||
Assert.False(isValid);
|
|
||||||
}
|
|
||||||
|
|
||||||
[Fact]
|
[Fact]
|
||||||
public async Task SelectAsync_PrefersActionWithConstraints()
|
public async Task SelectAsync_PrefersActionWithConstraints()
|
||||||
{
|
{
|
||||||
|
|
@ -652,7 +618,6 @@ namespace Microsoft.AspNet.Mvc.Infrastructure
|
||||||
};
|
};
|
||||||
|
|
||||||
var defaultActionSelector = new DefaultActionSelector(
|
var defaultActionSelector = new DefaultActionSelector(
|
||||||
actionDescriptorsCollectionProvider,
|
|
||||||
decisionTreeProvider,
|
decisionTreeProvider,
|
||||||
actionConstraintProviders,
|
actionConstraintProviders,
|
||||||
NullLoggerFactory.Instance);
|
NullLoggerFactory.Instance);
|
||||||
|
|
@ -737,7 +702,6 @@ namespace Microsoft.AspNet.Mvc.Infrastructure
|
||||||
};
|
};
|
||||||
|
|
||||||
return new DefaultActionSelector(
|
return new DefaultActionSelector(
|
||||||
actionProvider.Object,
|
|
||||||
decisionTreeProvider,
|
decisionTreeProvider,
|
||||||
actionConstraintProviders,
|
actionConstraintProviders,
|
||||||
loggerFactory);
|
loggerFactory);
|
||||||
|
|
|
||||||
|
|
@ -991,7 +991,6 @@ namespace Microsoft.AspNet.Mvc.Routing
|
||||||
var target = new Mock<IRouter>(MockBehavior.Strict);
|
var target = new Mock<IRouter>(MockBehavior.Strict);
|
||||||
target
|
target
|
||||||
.Setup(router => router.GetVirtualPath(It.IsAny<VirtualPathContext>()))
|
.Setup(router => router.GetVirtualPath(It.IsAny<VirtualPathContext>()))
|
||||||
.Callback<VirtualPathContext>(context => context.IsBound = true)
|
|
||||||
.Returns<VirtualPathContext>(context => null);
|
.Returns<VirtualPathContext>(context => null);
|
||||||
routeBuilder.DefaultHandler = target.Object;
|
routeBuilder.DefaultHandler = target.Object;
|
||||||
|
|
||||||
|
|
@ -1006,7 +1005,6 @@ namespace Microsoft.AspNet.Mvc.Routing
|
||||||
var mockHttpRoute = new Mock<IRouter>();
|
var mockHttpRoute = new Mock<IRouter>();
|
||||||
mockHttpRoute
|
mockHttpRoute
|
||||||
.Setup(mock => mock.GetVirtualPath(It.Is<VirtualPathContext>(c => string.Equals(c.RouteName, mockRouteName))))
|
.Setup(mock => mock.GetVirtualPath(It.Is<VirtualPathContext>(c => string.Equals(c.RouteName, mockRouteName))))
|
||||||
.Callback<VirtualPathContext>(c => c.IsBound = true)
|
|
||||||
.Returns(new VirtualPathData(mockHttpRoute.Object, mockTemplateValue));
|
.Returns(new VirtualPathData(mockHttpRoute.Object, mockTemplateValue));
|
||||||
|
|
||||||
routeBuilder.Routes.Add(mockHttpRoute.Object);
|
routeBuilder.Routes.Add(mockHttpRoute.Object);
|
||||||
|
|
@ -1017,7 +1015,6 @@ namespace Microsoft.AspNet.Mvc.Routing
|
||||||
{
|
{
|
||||||
public VirtualPathData GetVirtualPath(VirtualPathContext context)
|
public VirtualPathData GetVirtualPath(VirtualPathContext context)
|
||||||
{
|
{
|
||||||
context.IsBound = true;
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,42 +0,0 @@
|
||||||
// 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;
|
|
||||||
using System.Net.Http;
|
|
||||||
using System.Threading.Tasks;
|
|
||||||
using Xunit;
|
|
||||||
|
|
||||||
namespace Microsoft.AspNet.Mvc.FunctionalTests
|
|
||||||
{
|
|
||||||
|
|
||||||
public class BestEffortLinkGenerationTest : IClassFixture<MvcTestFixture<BestEffortLinkGenerationWebSite.Startup>>
|
|
||||||
{
|
|
||||||
private const string ExpectedOutput = @"<html>
|
|
||||||
<body>
|
|
||||||
<a href=""/Home/About"">About Us</a>
|
|
||||||
</body>
|
|
||||||
</html>";
|
|
||||||
|
|
||||||
public BestEffortLinkGenerationTest(MvcTestFixture<BestEffortLinkGenerationWebSite.Startup> fixture)
|
|
||||||
{
|
|
||||||
Client = fixture.Client;
|
|
||||||
}
|
|
||||||
|
|
||||||
public HttpClient Client { get; }
|
|
||||||
|
|
||||||
[Fact]
|
|
||||||
public async Task GenerateLink_NonExistentAction()
|
|
||||||
{
|
|
||||||
// Arrange
|
|
||||||
var url = "http://localhost/Home/Index";
|
|
||||||
|
|
||||||
// Act
|
|
||||||
var response = await Client.GetAsync(url);
|
|
||||||
var content = await response.Content.ReadAsStringAsync();
|
|
||||||
|
|
||||||
// Assert
|
|
||||||
Assert.Equal(HttpStatusCode.OK, response.StatusCode);
|
|
||||||
Assert.Equal(ExpectedOutput, content, ignoreLineEndingDifferences: true);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -14,7 +14,6 @@
|
||||||
"ApiExplorerWebSite": "1.0.0",
|
"ApiExplorerWebSite": "1.0.0",
|
||||||
"ApplicationModelWebSite": "1.0.0",
|
"ApplicationModelWebSite": "1.0.0",
|
||||||
"BasicWebSite": "1.0.0",
|
"BasicWebSite": "1.0.0",
|
||||||
"BestEffortLinkGenerationWebSite": "1.0.0",
|
|
||||||
"CompositeViewEngineWebSite": "1.0.0",
|
"CompositeViewEngineWebSite": "1.0.0",
|
||||||
"ContentNegotiationWebSite": "1.0.0",
|
"ContentNegotiationWebSite": "1.0.0",
|
||||||
"ControllerDiscoveryConventionsWebSite": "1.0.0",
|
"ControllerDiscoveryConventionsWebSite": "1.0.0",
|
||||||
|
|
|
||||||
|
|
@ -194,18 +194,6 @@ namespace Microsoft.AspNet.Mvc
|
||||||
Assert.Equal("No URL for remote validation could be found.", exception.Message);
|
Assert.Equal("No URL for remote validation could be found.", exception.Message);
|
||||||
}
|
}
|
||||||
|
|
||||||
[Fact]
|
|
||||||
public void GetClientValidationRules_WithActionController_NoController_Throws()
|
|
||||||
{
|
|
||||||
// Arrange
|
|
||||||
var attribute = new RemoteAttribute("Action", "Controller");
|
|
||||||
var context = GetValidationContextWithNoController();
|
|
||||||
|
|
||||||
// Act & Assert
|
|
||||||
var exception = Assert.Throws<InvalidOperationException>(() => attribute.GetClientValidationRules(context));
|
|
||||||
Assert.Equal("No URL for remote validation could be found.", exception.Message);
|
|
||||||
}
|
|
||||||
|
|
||||||
[Fact]
|
[Fact]
|
||||||
public void GetClientValidationRules_WithRoute_CallsUrlHelperWithExpectedValues()
|
public void GetClientValidationRules_WithRoute_CallsUrlHelperWithExpectedValues()
|
||||||
{
|
{
|
||||||
|
|
@ -505,35 +493,9 @@ namespace Microsoft.AspNet.Mvc
|
||||||
return new ClientModelValidationContext(actionContext, _metadata, _metadataProvider);
|
return new ClientModelValidationContext(actionContext, _metadata, _metadataProvider);
|
||||||
}
|
}
|
||||||
|
|
||||||
private static ClientModelValidationContext GetValidationContextWithNoController()
|
|
||||||
{
|
|
||||||
var serviceCollection = GetServiceCollection();
|
|
||||||
var serviceProvider = serviceCollection.BuildServiceProvider();
|
|
||||||
var routeCollection = GetRouteCollectionWithNoController(serviceProvider);
|
|
||||||
var routeData = new RouteData
|
|
||||||
{
|
|
||||||
Routers =
|
|
||||||
{
|
|
||||||
routeCollection,
|
|
||||||
},
|
|
||||||
};
|
|
||||||
|
|
||||||
var context = GetActionContext(serviceProvider, routeData);
|
|
||||||
var urlHelper = new UrlHelper(context);
|
|
||||||
var factory = new Mock<IUrlHelperFactory>();
|
|
||||||
factory
|
|
||||||
.Setup(f => f.GetUrlHelper(It.IsAny<ActionContext>()))
|
|
||||||
.Returns(urlHelper);
|
|
||||||
|
|
||||||
serviceCollection.AddSingleton<IUrlHelperFactory>(factory.Object);
|
|
||||||
context.HttpContext.RequestServices = serviceCollection.BuildServiceProvider();
|
|
||||||
|
|
||||||
return new ClientModelValidationContext(context, _metadata, _metadataProvider);
|
|
||||||
}
|
|
||||||
|
|
||||||
private static IRouter GetRouteCollectionWithArea(IServiceProvider serviceProvider)
|
private static IRouter GetRouteCollectionWithArea(IServiceProvider serviceProvider)
|
||||||
{
|
{
|
||||||
var builder = GetRouteBuilder(serviceProvider, isBound: true);
|
var builder = GetRouteBuilder(serviceProvider);
|
||||||
|
|
||||||
// Setting IsBound to true makes order more important than usual. First try the route that requires the
|
// Setting IsBound to true makes order more important than usual. First try the route that requires the
|
||||||
// area value. Skip usual "area:exists" constraint because that isn't relevant for link generation and it
|
// area value. Skip usual "area:exists" constraint because that isn't relevant for link generation and it
|
||||||
|
|
@ -546,13 +508,13 @@ namespace Microsoft.AspNet.Mvc
|
||||||
|
|
||||||
private static IRouter GetRouteCollectionWithNoController(IServiceProvider serviceProvider)
|
private static IRouter GetRouteCollectionWithNoController(IServiceProvider serviceProvider)
|
||||||
{
|
{
|
||||||
var builder = GetRouteBuilder(serviceProvider, isBound: false);
|
var builder = GetRouteBuilder(serviceProvider);
|
||||||
builder.MapRoute("default", "static/route");
|
builder.MapRoute("default", "static/route");
|
||||||
|
|
||||||
return builder.Build();
|
return builder.Build();
|
||||||
}
|
}
|
||||||
|
|
||||||
private static RouteBuilder GetRouteBuilder(IServiceProvider serviceProvider, bool isBound)
|
private static RouteBuilder GetRouteBuilder(IServiceProvider serviceProvider)
|
||||||
{
|
{
|
||||||
var builder = new RouteBuilder
|
var builder = new RouteBuilder
|
||||||
{
|
{
|
||||||
|
|
@ -562,7 +524,6 @@ namespace Microsoft.AspNet.Mvc
|
||||||
var handler = new Mock<IRouter>(MockBehavior.Strict);
|
var handler = new Mock<IRouter>(MockBehavior.Strict);
|
||||||
handler
|
handler
|
||||||
.Setup(router => router.GetVirtualPath(It.IsAny<VirtualPathContext>()))
|
.Setup(router => router.GetVirtualPath(It.IsAny<VirtualPathContext>()))
|
||||||
.Callback<VirtualPathContext>(context => context.IsBound = isBound)
|
|
||||||
.Returns((VirtualPathData)null);
|
.Returns((VirtualPathData)null);
|
||||||
builder.DefaultHandler = handler.Object;
|
builder.DefaultHandler = handler.Object;
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -1,18 +0,0 @@
|
||||||
<?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>b11c99c9-e577-4ca2-ac53-4f20ea71ad34</ProjectGuid>
|
|
||||||
<BaseIntermediateOutputPath Condition="'$(BaseIntermediateOutputPath)'=='' ">..\..\..\artifacts\obj\$(MSBuildProjectName)</BaseIntermediateOutputPath>
|
|
||||||
<OutputPath Condition="'$(OutputPath)'=='' ">..\..\..\artifacts\bin\$(MSBuildProjectName)\</OutputPath>
|
|
||||||
</PropertyGroup>
|
|
||||||
<PropertyGroup>
|
|
||||||
<SchemaVersion>2.0</SchemaVersion>
|
|
||||||
<DevelopmentServerPort>11623</DevelopmentServerPort>
|
|
||||||
</PropertyGroup>
|
|
||||||
<Import Project="$(VSToolsPath)\DNX\Microsoft.DNX.targets" Condition="'$(VSToolsPath)' != ''" />
|
|
||||||
</Project>
|
|
||||||
|
|
@ -1,15 +0,0 @@
|
||||||
// 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.Mvc;
|
|
||||||
|
|
||||||
namespace BestEffortLinkGenerationWebSite
|
|
||||||
{
|
|
||||||
public class HomeController : Controller
|
|
||||||
{
|
|
||||||
public IActionResult Index()
|
|
||||||
{
|
|
||||||
return View();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -1,30 +0,0 @@
|
||||||
// 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.Routing;
|
|
||||||
using Microsoft.Extensions.DependencyInjection;
|
|
||||||
|
|
||||||
namespace BestEffortLinkGenerationWebSite
|
|
||||||
{
|
|
||||||
public class Startup
|
|
||||||
{
|
|
||||||
// Set up application services
|
|
||||||
public void ConfigureServices(IServiceCollection services)
|
|
||||||
{
|
|
||||||
services.AddMvc();
|
|
||||||
|
|
||||||
services.Configure<RouteOptions>((options) =>
|
|
||||||
{
|
|
||||||
options.UseBestEffortLinkGeneration = true;
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
public void Configure(IApplicationBuilder app)
|
|
||||||
{
|
|
||||||
app.UseCultureReplacer();
|
|
||||||
|
|
||||||
app.UseMvcWithDefaultRoute();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
@ -1,5 +0,0 @@
|
||||||
<html>
|
|
||||||
<body>
|
|
||||||
@Html.ActionLink("About Us", "About")
|
|
||||||
</body>
|
|
||||||
</html>
|
|
||||||
|
|
@ -1,18 +0,0 @@
|
||||||
{
|
|
||||||
"commands": {
|
|
||||||
"web": "Microsoft.AspNet.Hosting server=Microsoft.AspNet.Server.WebListener server.urls=http://localhost:5001",
|
|
||||||
"kestrel": "Microsoft.AspNet.Hosting --server Microsoft.AspNet.Server.Kestrel --server.urls http://localhost:5000"
|
|
||||||
},
|
|
||||||
"dependencies": {
|
|
||||||
"Microsoft.AspNet.Server.Kestrel": "1.0.0-*",
|
|
||||||
"Microsoft.AspNet.Mvc": "6.0.0-*",
|
|
||||||
"Microsoft.AspNet.Mvc.TestConfiguration": "1.0.0",
|
|
||||||
"Microsoft.AspNet.Server.WebListener": "1.0.0-*",
|
|
||||||
"Microsoft.AspNet.StaticFiles": "1.0.0-*"
|
|
||||||
},
|
|
||||||
"frameworks": {
|
|
||||||
"dnx451": { },
|
|
||||||
"dnxcore50": { }
|
|
||||||
},
|
|
||||||
"webroot": "wwwroot"
|
|
||||||
}
|
|
||||||
|
|
@ -1,5 +0,0 @@
|
||||||
BestEffortLinkGenerationWebSite
|
|
||||||
===
|
|
||||||
|
|
||||||
This web site illustrates how to use best-effort link generation, which will allow conventional
|
|
||||||
routes to generate a link to an action which doesn't exist.
|
|
||||||
|
|
@ -1 +0,0 @@
|
||||||
HelloWorld
|
|
||||||
Loading…
Reference in New Issue