Rename EndpointFeature -> EndpointSelectorContext
This commit is contained in:
parent
1223752517
commit
1f5eec1d55
|
|
@ -129,7 +129,7 @@ namespace Microsoft.AspNetCore.Routing
|
|||
protected (HttpContext httpContext, RouteValueDictionary ambientValues) CreateCurrentRequestContext(
|
||||
object ambientValues = null)
|
||||
{
|
||||
var feature = new EndpointFeature { RouteValues = new RouteValueDictionary(ambientValues) };
|
||||
var feature = new EndpointSelectorContext { RouteValues = new RouteValueDictionary(ambientValues) };
|
||||
var context = new DefaultHttpContext();
|
||||
context.Features.Set<IEndpointFeature>(feature);
|
||||
context.Features.Set<IRouteValuesFeature>(feature);
|
||||
|
|
|
|||
|
|
@ -15,7 +15,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
private Matcher _dfa;
|
||||
|
||||
private int[] _samples;
|
||||
private EndpointFeature _feature;
|
||||
private EndpointSelectorContext _feature;
|
||||
|
||||
[GlobalSetup]
|
||||
public void Setup()
|
||||
|
|
@ -31,7 +31,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
_baseline = (BarebonesMatcher)SetupMatcher(new BarebonesMatcherBuilder());
|
||||
_dfa = SetupMatcher(CreateDfaMatcherBuilder());
|
||||
|
||||
_feature = new EndpointFeature();
|
||||
_feature = new EndpointSelectorContext();
|
||||
}
|
||||
|
||||
[Benchmark(Baseline = true, OperationsPerInvoke = SampleCount)]
|
||||
|
|
|
|||
|
|
@ -16,7 +16,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
private TrivialMatcher _baseline;
|
||||
private DfaMatcher _dfa;
|
||||
|
||||
private EndpointFeature _feature;
|
||||
private EndpointSelectorContext _feature;
|
||||
|
||||
[GlobalSetup]
|
||||
public void Setup()
|
||||
|
|
@ -28,7 +28,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
_baseline = (TrivialMatcher)SetupMatcher(new TrivialMatcherBuilder());
|
||||
_dfa = (DfaMatcher)SetupMatcher(CreateDfaMatcherBuilder());
|
||||
|
||||
_feature = new EndpointFeature();
|
||||
_feature = new EndpointSelectorContext();
|
||||
}
|
||||
|
||||
private void SetupEndpoints()
|
||||
|
|
|
|||
|
|
@ -14,7 +14,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
private BarebonesMatcher _baseline;
|
||||
private Matcher _dfa;
|
||||
|
||||
private EndpointFeature _feature;
|
||||
private EndpointSelectorContext _feature;
|
||||
|
||||
[GlobalSetup]
|
||||
public void Setup()
|
||||
|
|
@ -26,7 +26,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
_baseline = (BarebonesMatcher)SetupMatcher(new BarebonesMatcherBuilder());
|
||||
_dfa = SetupMatcher(CreateDfaMatcherBuilder());
|
||||
|
||||
_feature = new EndpointFeature();
|
||||
_feature = new EndpointSelectorContext();
|
||||
}
|
||||
|
||||
[Benchmark(Baseline = true, OperationsPerInvoke = EndpointCount)]
|
||||
|
|
|
|||
|
|
@ -18,7 +18,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
private Matcher _route;
|
||||
private Matcher _tree;
|
||||
|
||||
private EndpointFeature _feature;
|
||||
private EndpointSelectorContext _feature;
|
||||
|
||||
[GlobalSetup]
|
||||
public void Setup()
|
||||
|
|
@ -36,7 +36,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
_route = SetupMatcher(new RouteMatcherBuilder());
|
||||
_tree = SetupMatcher(new TreeRouterMatcherBuilder());
|
||||
|
||||
_feature = new EndpointFeature();
|
||||
_feature = new EndpointSelectorContext();
|
||||
}
|
||||
|
||||
private Matcher SetupMatcher(MatcherBuilder builder)
|
||||
|
|
|
|||
|
|
@ -23,23 +23,23 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
_candidates = new Candidate[] { new Candidate(endpoint), };
|
||||
}
|
||||
|
||||
public sealed override Task MatchAsync(HttpContext httpContext, EndpointFeature feature)
|
||||
public sealed override Task MatchAsync(HttpContext httpContext, EndpointSelectorContext context)
|
||||
{
|
||||
if (httpContext == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(httpContext));
|
||||
}
|
||||
|
||||
if (feature == null)
|
||||
if (context == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(feature));
|
||||
throw new ArgumentNullException(nameof(context));
|
||||
}
|
||||
|
||||
var path = httpContext.Request.Path.Value;
|
||||
if (string.Equals(_endpoint.RoutePattern.RawText, path, StringComparison.OrdinalIgnoreCase))
|
||||
{
|
||||
feature.Endpoint = _endpoint;
|
||||
feature.RouteValues = new RouteValueDictionary();
|
||||
context.Endpoint = _endpoint;
|
||||
context.RouteValues = new RouteValueDictionary();
|
||||
}
|
||||
|
||||
return Task.CompletedTask;
|
||||
|
|
|
|||
|
|
@ -55,7 +55,7 @@ namespace Microsoft.AspNetCore.Routing
|
|||
|
||||
public async Task Invoke(HttpContext httpContext)
|
||||
{
|
||||
var feature = new EndpointFeature();
|
||||
var feature = new EndpointSelectorContext();
|
||||
|
||||
// There's an inherent race condition between waiting for init and accessing the matcher
|
||||
// this is OK because once `_matcher` is initialized, it will not be set to null again.
|
||||
|
|
@ -66,7 +66,7 @@ namespace Microsoft.AspNetCore.Routing
|
|||
{
|
||||
// Set the endpoint feature only on success. This means we won't overwrite any
|
||||
// existing state for related features unless we did something.
|
||||
SetEndpointFeature(httpContext, feature);
|
||||
SetFeatures(httpContext, feature);
|
||||
|
||||
Log.MatchSuccess(_logger, feature);
|
||||
}
|
||||
|
|
@ -78,13 +78,13 @@ namespace Microsoft.AspNetCore.Routing
|
|||
await _next(httpContext);
|
||||
}
|
||||
|
||||
private static void SetEndpointFeature(HttpContext httpContext, EndpointFeature feature)
|
||||
private static void SetFeatures(HttpContext httpContext, EndpointSelectorContext context)
|
||||
{
|
||||
// For back-compat EndpointRouteValuesFeature implements IEndpointFeature,
|
||||
// IRouteValuesFeature and IRoutingFeature
|
||||
httpContext.Features.Set<IRoutingFeature>(feature);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(feature);
|
||||
httpContext.Features.Set<IEndpointFeature>(feature);
|
||||
httpContext.Features.Set<IRoutingFeature>(context);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(context);
|
||||
httpContext.Features.Set<IEndpointFeature>(context);
|
||||
}
|
||||
|
||||
// Initialization is async to avoid blocking threads while reflection and things
|
||||
|
|
@ -126,9 +126,9 @@ namespace Microsoft.AspNetCore.Routing
|
|||
new EventId(2, "MatchFailure"),
|
||||
"Request did not match any endpoints.");
|
||||
|
||||
public static void MatchSuccess(ILogger logger, EndpointFeature feature)
|
||||
public static void MatchSuccess(ILogger logger, EndpointSelectorContext context)
|
||||
{
|
||||
_matchSuccess(logger, feature.Endpoint.DisplayName, null);
|
||||
_matchSuccess(logger, context.Endpoint.DisplayName, null);
|
||||
}
|
||||
|
||||
public static void MatchFailure(ILogger logger)
|
||||
|
|
|
|||
|
|
@ -7,7 +7,7 @@ using Microsoft.AspNetCore.Http.Features;
|
|||
|
||||
namespace Microsoft.AspNetCore.Routing
|
||||
{
|
||||
public sealed class EndpointFeature : IEndpointFeature, IRouteValuesFeature, IRoutingFeature
|
||||
public sealed class EndpointSelectorContext : IEndpointFeature, IRouteValuesFeature, IRoutingFeature
|
||||
{
|
||||
private RouteData _routeData;
|
||||
private RouteValueDictionary _routeValues;
|
||||
|
|
@ -27,9 +27,9 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
// Used in tests
|
||||
internal Matcher CurrentMatcher => _cache.Value;
|
||||
|
||||
public override Task MatchAsync(HttpContext httpContext, EndpointFeature feature)
|
||||
public override Task MatchAsync(HttpContext httpContext, EndpointSelectorContext context)
|
||||
{
|
||||
return CurrentMatcher.MatchAsync(httpContext, feature);
|
||||
return CurrentMatcher.MatchAsync(httpContext, context);
|
||||
}
|
||||
|
||||
private Matcher CreateMatcher(IReadOnlyList<Endpoint> endpoints)
|
||||
|
|
|
|||
|
|
@ -6,7 +6,6 @@ using System.Collections.Generic;
|
|||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.AspNetCore.Http.Features;
|
||||
|
||||
namespace Microsoft.AspNetCore.Routing.Matching
|
||||
{
|
||||
|
|
@ -26,26 +25,26 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
|
||||
public override async Task SelectAsync(
|
||||
HttpContext httpContext,
|
||||
EndpointFeature feature,
|
||||
EndpointSelectorContext context,
|
||||
CandidateSet candidateSet)
|
||||
{
|
||||
var selectorPolicies = _selectorPolicies;
|
||||
for (var i = 0; i < _selectorPolicies.Length; i++)
|
||||
{
|
||||
await selectorPolicies[i].ApplyAsync(httpContext, feature, candidateSet);
|
||||
if (feature.Endpoint != null)
|
||||
await selectorPolicies[i].ApplyAsync(httpContext, context, candidateSet);
|
||||
if (context.Endpoint != null)
|
||||
{
|
||||
// This is a short circuit, the selector chose an endpoint.
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
ProcessFinalCandidates(httpContext, feature, candidateSet);
|
||||
ProcessFinalCandidates(httpContext, context, candidateSet);
|
||||
}
|
||||
|
||||
private static void ProcessFinalCandidates(
|
||||
HttpContext httpContext,
|
||||
EndpointFeature feature,
|
||||
EndpointSelectorContext context,
|
||||
CandidateSet candidateSet)
|
||||
{
|
||||
Endpoint endpoint = null;
|
||||
|
|
@ -87,8 +86,8 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
|
||||
if (endpoint != null)
|
||||
{
|
||||
feature.Endpoint = endpoint;
|
||||
feature.RouteValues = values;
|
||||
context.Endpoint = endpoint;
|
||||
context.RouteValues = values;
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -23,16 +23,16 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
_maxSegmentCount = maxSegmentCount;
|
||||
}
|
||||
|
||||
public sealed override Task MatchAsync(HttpContext httpContext, EndpointFeature feature)
|
||||
public sealed override Task MatchAsync(HttpContext httpContext, EndpointSelectorContext context)
|
||||
{
|
||||
if (httpContext == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(httpContext));
|
||||
}
|
||||
|
||||
if (feature == null)
|
||||
if (context == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(feature));
|
||||
throw new ArgumentNullException(nameof(context));
|
||||
}
|
||||
|
||||
// The sequence of actions we take is optimized to avoid doing expensive work
|
||||
|
|
@ -132,7 +132,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
state.IsValidCandidate = isMatch;
|
||||
}
|
||||
|
||||
return _selector.SelectAsync(httpContext, feature, candidateSet);
|
||||
return _selector.SelectAsync(httpContext, context, candidateSet);
|
||||
}
|
||||
|
||||
internal Candidate[] FindCandidateSet(
|
||||
|
|
|
|||
|
|
@ -18,16 +18,16 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
/// Asynchronously selects an <see cref="Endpoint"/> from the <see cref="CandidateSet"/>.
|
||||
/// </summary>
|
||||
/// <param name="httpContext">The <see cref="HttpContext"/> associated with the current request.</param>
|
||||
/// <param name="feature">The <see cref="IEndpointFeature"/> associated with the current request.</param>
|
||||
/// <param name="context">The <see cref="EndpointSelectorContext"/> associated with the current request.</param>
|
||||
/// <param name="candidates">The <see cref="CandidateSet"/>.</param>
|
||||
/// <returns>A <see cref="Task"/> that completes asynchronously once endpoint selection is complete.</returns>
|
||||
/// <remarks>
|
||||
/// An <see cref="EndpointSelector"/> should assign the <see cref="EndpointFeature.Endpoint"/>
|
||||
/// and <see cref="EndpointFeature.RouteValues"/> properties once an endpoint is selected.
|
||||
/// An <see cref="EndpointSelector"/> should assign the <see cref="EndpointSelectorContext.Endpoint"/>
|
||||
/// and <see cref="EndpointSelectorContext.RouteValues"/> properties once an endpoint is selected.
|
||||
/// </remarks>
|
||||
public abstract Task SelectAsync(
|
||||
HttpContext httpContext,
|
||||
EndpointFeature feature,
|
||||
EndpointSelectorContext context,
|
||||
CandidateSet candidates);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -20,8 +20,8 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
/// <param name="httpContext">
|
||||
/// The <see cref="HttpContext"/> associated with the current request.
|
||||
/// </param>
|
||||
/// <param name="feature">
|
||||
/// The <see cref="EndpointFeature"/> associated with the current request.
|
||||
/// <param name="context">
|
||||
/// The <see cref="EndpointSelectorContext"/> associated with the current request.
|
||||
/// </param>
|
||||
/// <param name="candidates">The <see cref="CandidateSet"/>.</param>
|
||||
/// <remarks>
|
||||
|
|
@ -31,10 +31,10 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
/// <see cref="CandidateState.IsValidCandidate"/> to <c>false</c> where desired.
|
||||
/// </para>
|
||||
/// <para>
|
||||
/// To signal an error condition, set <see cref="EndpointFeature.Endpoint"/> to an
|
||||
/// To signal an error condition, set <see cref="EndpointSelectorContext.Endpoint"/> to an
|
||||
/// <see cref="Endpoint"/> value that will produce the desired error when executed.
|
||||
/// </para>
|
||||
/// </remarks>
|
||||
Task ApplyAsync(HttpContext httpContext, EndpointFeature feature, CandidateSet candidates);
|
||||
Task ApplyAsync(HttpContext httpContext, EndpointSelectorContext context, CandidateSet candidates);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -17,10 +17,10 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
/// Attempts to asynchronously select an <see cref="Endpoint"/> for the current request.
|
||||
/// </summary>
|
||||
/// <param name="httpContext">The <see cref="HttpContext"/> associated with the current request.</param>
|
||||
/// <param name="feature">
|
||||
/// <param name="context">
|
||||
/// The <see cref="IEndpointFeature"/> associated with the current request. The
|
||||
/// <see cref="EndpointFeature"/> will be mutated to contain the result of the operation.</param>
|
||||
/// <see cref="EndpointSelectorContext"/> will be mutated to contain the result of the operation.</param>
|
||||
/// <returns>A <see cref="Task"/> which represents the asynchronous completion of the operation.</returns>
|
||||
public abstract Task MatchAsync(HttpContext httpContext, EndpointFeature feature);
|
||||
public abstract Task MatchAsync(HttpContext httpContext, EndpointSelectorContext context);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -39,7 +39,7 @@ namespace Microsoft.AspNetCore.Routing
|
|||
var httpContext = new DefaultHttpContext();
|
||||
httpContext.RequestServices = new ServiceProvider();
|
||||
|
||||
httpContext.Features.Set<IEndpointFeature>(new EndpointFeature()
|
||||
httpContext.Features.Set<IEndpointFeature>(new EndpointSelectorContext()
|
||||
{
|
||||
Endpoint = null,
|
||||
});
|
||||
|
|
@ -71,7 +71,7 @@ namespace Microsoft.AspNetCore.Routing
|
|||
return Task.CompletedTask;
|
||||
};
|
||||
|
||||
httpContext.Features.Set<IEndpointFeature>(new EndpointFeature()
|
||||
httpContext.Features.Set<IEndpointFeature>(new EndpointSelectorContext()
|
||||
{
|
||||
Endpoint = new Endpoint(endpointFunc, EndpointMetadataCollection.Empty, "Test"),
|
||||
});
|
||||
|
|
|
|||
|
|
@ -105,11 +105,11 @@ namespace Microsoft.AspNetCore.Routing
|
|||
|
||||
private HttpContext CreateHttpContext()
|
||||
{
|
||||
var feature = new EndpointFeature();
|
||||
var context = new EndpointSelectorContext();
|
||||
|
||||
var httpContext = new DefaultHttpContext();
|
||||
httpContext.Features.Set<IEndpointFeature>(feature);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(feature);
|
||||
httpContext.Features.Set<IEndpointFeature>(context);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(context);
|
||||
|
||||
httpContext.RequestServices = new TestServiceProvider();
|
||||
|
||||
|
|
|
|||
|
|
@ -9,7 +9,7 @@ using Xunit;
|
|||
|
||||
namespace Microsoft.AspNetCore.Routing
|
||||
{
|
||||
public class EndpointFeatureTest
|
||||
public class EndpointSelectorContextTest
|
||||
{
|
||||
[Fact]
|
||||
public void RouteData_CanIntializeDataTokens_WithMetadata()
|
||||
|
|
@ -17,7 +17,7 @@ namespace Microsoft.AspNetCore.Routing
|
|||
// Arrange
|
||||
var expected = new RouteValueDictionary(new { foo = 17, bar = "hello", });
|
||||
|
||||
var feature = new EndpointFeature()
|
||||
var context = new EndpointSelectorContext()
|
||||
{
|
||||
Endpoint = new RouteEndpoint(
|
||||
TestConstants.EmptyRequestDelegate,
|
||||
|
|
@ -28,7 +28,7 @@ namespace Microsoft.AspNetCore.Routing
|
|||
};
|
||||
|
||||
// Act
|
||||
var routeData = ((IRoutingFeature)feature).RouteData;
|
||||
var routeData = ((IRoutingFeature)context).RouteData;
|
||||
|
||||
// Assert
|
||||
Assert.NotSame(expected, routeData.DataTokens);
|
||||
|
|
@ -39,7 +39,7 @@ namespace Microsoft.AspNetCore.Routing
|
|||
public void RouteData_DataTokensIsEmpty_WithoutMetadata()
|
||||
{
|
||||
// Arrange
|
||||
var feature = new EndpointFeature()
|
||||
var context = new EndpointSelectorContext()
|
||||
{
|
||||
Endpoint = new RouteEndpoint(
|
||||
TestConstants.EmptyRequestDelegate,
|
||||
|
|
@ -50,7 +50,7 @@ namespace Microsoft.AspNetCore.Routing
|
|||
};
|
||||
|
||||
// Act
|
||||
var routeData = ((IRoutingFeature)feature).RouteData;
|
||||
var routeData = ((IRoutingFeature)context).RouteData;
|
||||
|
||||
// Assert
|
||||
Assert.Empty(routeData.DataTokens);
|
||||
|
|
@ -26,12 +26,12 @@ namespace Microsoft.AspNetCore.Routing
|
|||
|
||||
var linkGenerator = CreateLinkGenerator(endpoint1, endpoint2);
|
||||
|
||||
var feature = new EndpointFeature()
|
||||
var context = new EndpointSelectorContext()
|
||||
{
|
||||
RouteValues = new RouteValueDictionary(new { p = "5", })
|
||||
};
|
||||
var httpContext = CreateHttpContext();
|
||||
httpContext.Features.Set<IRouteValuesFeature>(feature);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(context);
|
||||
httpContext.Request.PathBase = new PathString("/Foo/Bar?encodeme?");
|
||||
|
||||
var values = new { query = "some?query", };
|
||||
|
|
|
|||
|
|
@ -32,12 +32,12 @@ namespace Microsoft.AspNetCore.Routing
|
|||
|
||||
var linkGenerator = CreateLinkGenerator(endpoint1, endpoint2);
|
||||
|
||||
var feature = new EndpointFeature()
|
||||
var context = new EndpointSelectorContext()
|
||||
{
|
||||
RouteValues = new RouteValueDictionary(new { action = "Index", })
|
||||
};
|
||||
var httpContext = CreateHttpContext();
|
||||
httpContext.Features.Set<IRouteValuesFeature>(feature);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(context);
|
||||
httpContext.Request.PathBase = new PathString("/Foo/Bar?encodeme?");
|
||||
|
||||
// Act
|
||||
|
|
|
|||
|
|
@ -18,13 +18,13 @@ namespace Microsoft.AspNetCore.Routing
|
|||
{
|
||||
var httpContext = new DefaultHttpContext();
|
||||
|
||||
var feature = new EndpointFeature
|
||||
var context = new EndpointSelectorContext
|
||||
{
|
||||
RouteValues = new RouteValueDictionary(ambientValues)
|
||||
};
|
||||
|
||||
httpContext.Features.Set<IEndpointFeature>(feature);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(feature);
|
||||
httpContext.Features.Set<IEndpointFeature>(context);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(context);
|
||||
return httpContext;
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -20,16 +20,16 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
Matchers = matchers;
|
||||
}
|
||||
|
||||
public override Task MatchAsync(HttpContext httpContext, EndpointFeature feature)
|
||||
public override Task MatchAsync(HttpContext httpContext, EndpointSelectorContext context)
|
||||
{
|
||||
if (httpContext == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(httpContext));
|
||||
}
|
||||
|
||||
if (feature == null)
|
||||
if (context == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(feature));
|
||||
throw new ArgumentNullException(nameof(context));
|
||||
}
|
||||
|
||||
var path = httpContext.Request.Path.Value;
|
||||
|
|
@ -37,8 +37,8 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
if (Matchers[i].TryMatch(path))
|
||||
{
|
||||
feature.Endpoint = Matchers[i].Endpoint;
|
||||
feature.RouteValues = new RouteValueDictionary();
|
||||
context.Endpoint = Matchers[i].Endpoint;
|
||||
context.RouteValues = new RouteValueDictionary();
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -121,12 +121,12 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
return Array.Empty<Candidate>();
|
||||
}
|
||||
|
||||
public override Task MatchAsync(HttpContext httpContext, EndpointFeature feature)
|
||||
public override Task MatchAsync(HttpContext httpContext, EndpointSelectorContext context)
|
||||
{
|
||||
if (TryMatch(httpContext.Request.Path.Value))
|
||||
{
|
||||
feature.Endpoint = Endpoint;
|
||||
feature.RouteValues = new RouteValueDictionary();
|
||||
context.Endpoint = Endpoint;
|
||||
context.RouteValues = new RouteValueDictionary();
|
||||
}
|
||||
|
||||
return Task.CompletedTask;
|
||||
|
|
|
|||
|
|
@ -134,7 +134,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
public IReadOnlyList<RouteEndpoint> Endpoints { get; set; }
|
||||
|
||||
public override Task MatchAsync(HttpContext httpContext, EndpointFeature feature)
|
||||
public override Task MatchAsync(HttpContext httpContext, EndpointSelectorContext context)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
|
|
|||
|
|
@ -21,14 +21,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var scores = new int[] { };
|
||||
var candidateSet = CreateCandidateSet(endpoints, scores);
|
||||
|
||||
var (httpContext, feature) = CreateContext();
|
||||
var (httpContext, context) = CreateContext();
|
||||
var selector = CreateSelector();
|
||||
|
||||
// Act
|
||||
await selector.SelectAsync(httpContext, feature, candidateSet);
|
||||
await selector.SelectAsync(httpContext, context, candidateSet);
|
||||
|
||||
// Assert
|
||||
Assert.Null(feature.Endpoint);
|
||||
Assert.Null(context.Endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -42,14 +42,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
candidateSet[0].Values = new RouteValueDictionary();
|
||||
candidateSet[0].IsValidCandidate = false;
|
||||
|
||||
var (httpContext, feature) = CreateContext();
|
||||
var (httpContext, context) = CreateContext();
|
||||
var selector = CreateSelector();
|
||||
|
||||
// Act
|
||||
await selector.SelectAsync(httpContext, feature, candidateSet);
|
||||
await selector.SelectAsync(httpContext, context, candidateSet);
|
||||
|
||||
// Assert
|
||||
Assert.Null(feature.Endpoint);
|
||||
Assert.Null(context.Endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -63,14 +63,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
candidateSet[0].Values = new RouteValueDictionary();
|
||||
candidateSet[0].IsValidCandidate = true;
|
||||
|
||||
var (httpContext, feature) = CreateContext();
|
||||
var (httpContext, context) = CreateContext();
|
||||
var selector = CreateSelector();
|
||||
|
||||
// Act
|
||||
await selector.SelectAsync(httpContext, feature, candidateSet);
|
||||
await selector.SelectAsync(httpContext, context, candidateSet);
|
||||
|
||||
// Assert
|
||||
Assert.Same(endpoints[0], feature.Endpoint);
|
||||
Assert.Same(endpoints[0], context.Endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -84,14 +84,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
candidateSet[0].IsValidCandidate = false;
|
||||
candidateSet[1].IsValidCandidate = true;
|
||||
|
||||
var (httpContext, feature) = CreateContext();
|
||||
var (httpContext, context) = CreateContext();
|
||||
var selector = CreateSelector();
|
||||
|
||||
// Act
|
||||
await selector.SelectAsync(httpContext, feature, candidateSet);
|
||||
await selector.SelectAsync(httpContext, context, candidateSet);
|
||||
|
||||
// Assert
|
||||
Assert.Same(endpoints[1], feature.Endpoint);
|
||||
Assert.Same(endpoints[1], context.Endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -106,14 +106,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
candidateSet[1].IsValidCandidate = true;
|
||||
candidateSet[2].IsValidCandidate = true;
|
||||
|
||||
var (httpContext, feature) = CreateContext();
|
||||
var (httpContext, context) = CreateContext();
|
||||
var selector = CreateSelector();
|
||||
|
||||
// Act
|
||||
await selector.SelectAsync(httpContext, feature, candidateSet);
|
||||
await selector.SelectAsync(httpContext, context, candidateSet);
|
||||
|
||||
// Assert
|
||||
Assert.Same(endpoints[1], feature.Endpoint);
|
||||
Assert.Same(endpoints[1], context.Endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -137,14 +137,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
candidateSet[3].IsValidCandidate = false;
|
||||
candidateSet[4].IsValidCandidate = true;
|
||||
|
||||
var (httpContext, feature) = CreateContext();
|
||||
var (httpContext, context) = CreateContext();
|
||||
var selector = CreateSelector();
|
||||
|
||||
// Act
|
||||
await selector.SelectAsync(httpContext, feature, candidateSet);
|
||||
await selector.SelectAsync(httpContext, context, candidateSet);
|
||||
|
||||
// Assert
|
||||
Assert.Same(endpoints[4], feature.Endpoint);
|
||||
Assert.Same(endpoints[4], context.Endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -159,11 +159,11 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
candidateSet[1].IsValidCandidate = true;
|
||||
candidateSet[2].IsValidCandidate = true;
|
||||
|
||||
var (httpContext, feature) = CreateContext();
|
||||
var (httpContext, context) = CreateContext();
|
||||
var selector = CreateSelector();
|
||||
|
||||
// Act
|
||||
var ex = await Assert.ThrowsAsync<AmbiguousMatchException>(() => selector.SelectAsync(httpContext, feature, candidateSet));
|
||||
var ex = await Assert.ThrowsAsync<AmbiguousMatchException>(() => selector.SelectAsync(httpContext, context, candidateSet));
|
||||
|
||||
// Assert
|
||||
Assert.Equal(
|
||||
|
|
@ -171,7 +171,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
|
||||
test: /test2
|
||||
test: /test3", ex.Message);
|
||||
Assert.Null(feature.Endpoint);
|
||||
Assert.Null(context.Endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -185,8 +185,8 @@ test: /test3", ex.Message);
|
|||
var policy = new Mock<MatcherPolicy>();
|
||||
policy
|
||||
.As<IEndpointSelectorPolicy>()
|
||||
.Setup(p => p.ApplyAsync(It.IsAny<HttpContext>(), It.IsAny<EndpointFeature>(), It.IsAny<CandidateSet>()))
|
||||
.Returns<HttpContext, EndpointFeature, CandidateSet>((c, f, cs) =>
|
||||
.Setup(p => p.ApplyAsync(It.IsAny<HttpContext>(), It.IsAny<EndpointSelectorContext>(), It.IsAny<CandidateSet>()))
|
||||
.Returns<HttpContext, EndpointSelectorContext, CandidateSet>((c, f, cs) =>
|
||||
{
|
||||
cs[1].IsValidCandidate = false;
|
||||
return Task.CompletedTask;
|
||||
|
|
@ -196,14 +196,14 @@ test: /test3", ex.Message);
|
|||
candidateSet[1].IsValidCandidate = true;
|
||||
candidateSet[2].IsValidCandidate = true;
|
||||
|
||||
var (httpContext, feature) = CreateContext();
|
||||
var (httpContext, context) = CreateContext();
|
||||
var selector = CreateSelector(policy.Object);
|
||||
|
||||
// Act
|
||||
await selector.SelectAsync(httpContext, feature, candidateSet);
|
||||
await selector.SelectAsync(httpContext, context, candidateSet);
|
||||
|
||||
// Assert
|
||||
Assert.Same(endpoints[2], feature.Endpoint);
|
||||
Assert.Same(endpoints[2], context.Endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -217,8 +217,8 @@ test: /test3", ex.Message);
|
|||
var policy1 = new Mock<MatcherPolicy>();
|
||||
policy1
|
||||
.As<IEndpointSelectorPolicy>()
|
||||
.Setup(p => p.ApplyAsync(It.IsAny<HttpContext>(), It.IsAny<EndpointFeature>(), It.IsAny<CandidateSet>()))
|
||||
.Returns<HttpContext, EndpointFeature, CandidateSet>((c, f, cs) =>
|
||||
.Setup(p => p.ApplyAsync(It.IsAny<HttpContext>(), It.IsAny<EndpointSelectorContext>(), It.IsAny<CandidateSet>()))
|
||||
.Returns<HttpContext, EndpointSelectorContext, CandidateSet>((c, f, cs) =>
|
||||
{
|
||||
f.Endpoint = cs[0].Endpoint;
|
||||
return Task.CompletedTask;
|
||||
|
|
@ -231,31 +231,31 @@ test: /test3", ex.Message);
|
|||
.Returns(1000);
|
||||
policy2
|
||||
.As<IEndpointSelectorPolicy>()
|
||||
.Setup(p => p.ApplyAsync(It.IsAny<HttpContext>(), It.IsAny<EndpointFeature>(), It.IsAny<CandidateSet>()))
|
||||
.Setup(p => p.ApplyAsync(It.IsAny<HttpContext>(), It.IsAny<EndpointSelectorContext>(), It.IsAny<CandidateSet>()))
|
||||
.Throws(new InvalidOperationException());
|
||||
|
||||
candidateSet[0].IsValidCandidate = false;
|
||||
candidateSet[1].IsValidCandidate = true;
|
||||
candidateSet[2].IsValidCandidate = true;
|
||||
|
||||
var (httpContext, feature) = CreateContext();
|
||||
var (httpContext, context) = CreateContext();
|
||||
var selector = CreateSelector(policy1.Object, policy2.Object);
|
||||
|
||||
// Act
|
||||
await selector.SelectAsync(httpContext, feature, candidateSet);
|
||||
await selector.SelectAsync(httpContext, context, candidateSet);
|
||||
|
||||
// Assert
|
||||
Assert.Same(endpoints[0], feature.Endpoint);
|
||||
Assert.Same(endpoints[0], context.Endpoint);
|
||||
}
|
||||
|
||||
private static (HttpContext httpContext, EndpointFeature feature) CreateContext()
|
||||
private static (HttpContext httpContext, EndpointSelectorContext context) CreateContext()
|
||||
{
|
||||
var feature = new EndpointFeature();
|
||||
var context = new EndpointSelectorContext();
|
||||
var httpContext = new DefaultHttpContext();
|
||||
httpContext.Features.Set<IEndpointFeature>(feature);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(feature);
|
||||
httpContext.Features.Set<IEndpointFeature>(context);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(context);
|
||||
|
||||
return (httpContext, feature);
|
||||
return (httpContext, context);
|
||||
}
|
||||
|
||||
private static RouteEndpoint CreateEndpoint(string template)
|
||||
|
|
|
|||
|
|
@ -14,13 +14,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, keys, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, keys, values);
|
||||
}
|
||||
|
||||
internal override Matcher CreateMatcher(params RouteEndpoint[] endpoints)
|
||||
|
|
|
|||
|
|
@ -55,14 +55,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
|
||||
var matcher = CreateDfaMatcher(endpointDataSource);
|
||||
|
||||
var (httpContext, endpointFeature) = CreateHttpContext();
|
||||
var (httpContext, context) = CreateContext();
|
||||
httpContext.Request.Path = "/1";
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, endpointFeature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
Assert.NotNull(endpointFeature.Endpoint);
|
||||
Assert.NotNull(context.Endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -76,7 +76,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
|
||||
var matcher = CreateDfaMatcher(endpointDataSource);
|
||||
|
||||
var (httpContext, endpointFeature) = CreateHttpContext();
|
||||
var (httpContext, endpointFeature) = CreateContext();
|
||||
httpContext.Request.Path = "/One";
|
||||
|
||||
// Act
|
||||
|
|
@ -101,7 +101,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
|
||||
var matcher = CreateDfaMatcher(endpointDataSource);
|
||||
|
||||
var (httpContext, endpointFeature) = CreateHttpContext();
|
||||
var (httpContext, endpointFeature) = CreateContext();
|
||||
httpContext.Request.Path = "/Teams";
|
||||
|
||||
// Act
|
||||
|
|
@ -120,7 +120,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
|
||||
var endpointSelector = new Mock<EndpointSelector>();
|
||||
endpointSelector
|
||||
.Setup(s => s.SelectAsync(It.IsAny<HttpContext>(), It.IsAny<EndpointFeature>(), It.IsAny<CandidateSet>()))
|
||||
.Setup(s => s.SelectAsync(It.IsAny<HttpContext>(), It.IsAny<EndpointSelectorContext>(), It.IsAny<CandidateSet>()))
|
||||
.Callback<HttpContext, IEndpointFeature, CandidateSet>((c, f, cs) =>
|
||||
{
|
||||
Assert.Equal(2, cs.Count);
|
||||
|
|
@ -147,7 +147,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
|
||||
var matcher = CreateDfaMatcher(endpointDataSource, endpointSelector.Object);
|
||||
|
||||
var (httpContext, endpointFeature) = CreateHttpContext();
|
||||
var (httpContext, endpointFeature) = CreateContext();
|
||||
httpContext.Request.Path = "/Teams";
|
||||
|
||||
// Act
|
||||
|
|
@ -157,15 +157,15 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
Assert.Equal(endpoint2, endpointFeature.Endpoint);
|
||||
}
|
||||
|
||||
private (HttpContext httpContext, EndpointFeature feature) CreateHttpContext()
|
||||
private (HttpContext httpContext, EndpointSelectorContext context) CreateContext()
|
||||
{
|
||||
var feature = new EndpointFeature();
|
||||
var context = new EndpointSelectorContext();
|
||||
|
||||
var httpContext = new DefaultHttpContext();
|
||||
httpContext.Features.Set<IEndpointFeature>(feature);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(feature);
|
||||
httpContext.Features.Set<IEndpointFeature>(context);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(context);
|
||||
|
||||
return (httpContext, feature);
|
||||
return (httpContext, context);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -28,13 +28,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, keys, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, keys, values);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -43,13 +43,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
// Arrange
|
||||
var endpoint = CreateEndpoint("/a/{b}/{c}", new { b = "17", c = "18", });
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/a");
|
||||
var (httpContext, context) = CreateContext("/a");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, new { b = "17", c = "18", });
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, new { b = "17", c = "18", });
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -58,13 +58,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
// Arrange
|
||||
var endpoint = CreateEndpoint("/a/{b}/{c}", new { b = "17", c = "18", d = "19" });
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/a");
|
||||
var (httpContext, context) = CreateContext("/a");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, new { b = "17", c = "18", d = "19" });
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, new { b = "17", c = "18", d = "19" });
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -83,13 +83,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -115,13 +115,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, keys, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, keys, values);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -138,13 +138,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -162,13 +162,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, keys, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, keys, values);
|
||||
}
|
||||
|
||||
// Historically catchall segments don't match an empty segment, but only if it's
|
||||
|
|
@ -182,13 +182,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
|
||||
// Need to access these to prevent a warning from the xUnit analyzer.
|
||||
// Some of these tests will match (and process the values) and some will not.
|
||||
|
|
@ -217,13 +217,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, keys, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, keys, values);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -237,13 +237,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -266,13 +266,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, keys, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, keys, values);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -292,13 +292,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
}
|
||||
|
||||
// Most of are copied from old routing tests that date back to the VS 2010 era. Enjoy!
|
||||
|
|
@ -317,13 +317,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, keys, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, keys, values);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -347,13 +347,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
|
||||
// Arrange
|
||||
var matcher = CreateMatcher(other, expected);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, expected, ignoreValues: true);
|
||||
MatcherAssert.AssertMatch(context, httpContext, expected, ignoreValues: true);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -381,13 +381,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
|
||||
// Arrange
|
||||
var matcher = CreateMatcher(other, expected);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, expected, ignoreValues: true);
|
||||
MatcherAssert.AssertMatch(context, httpContext, expected, ignoreValues: true);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -434,13 +434,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var expected = endpoints[Array.IndexOf(templates, expectedTemplate)];
|
||||
|
||||
var matcher = CreateMatcher(endpoints);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, expected, ignoreValues: true);
|
||||
MatcherAssert.AssertMatch(context, httpContext, expected, ignoreValues: true);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -23,13 +23,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint = CreateEndpoint("/hello", httpMethods: new string[] { "GET", });
|
||||
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET");
|
||||
var (httpContext, context) = CreateContext("/hello", "GET");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -39,13 +39,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint = CreateEndpoint("/hello", httpMethods: new string[] { "GET", }, acceptCorsPreflight: true);
|
||||
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET");
|
||||
var (httpContext, context) = CreateContext("/hello", "GET");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -55,13 +55,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint = CreateEndpoint("/hello", httpMethods: new string[] { "GET", }, acceptCorsPreflight: true);
|
||||
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET", corsPreflight: true);
|
||||
var (httpContext, context) = CreateContext("/hello", "GET", corsPreflight: true);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
|
||||
|
|
@ -72,14 +72,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint = CreateEndpoint("/hello", httpMethods: new string[] { "GET", }, acceptCorsPreflight: false);
|
||||
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET", corsPreflight: true);
|
||||
var (httpContext, context) = CreateContext("/hello", "GET", corsPreflight: true);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
Assert.NotSame(endpoint, feature.Endpoint);
|
||||
Assert.Same(HttpMethodMatcherPolicy.Http405EndpointDisplayName, feature.Endpoint.DisplayName);
|
||||
Assert.NotSame(endpoint, context.Endpoint);
|
||||
Assert.Same(HttpMethodMatcherPolicy.Http405EndpointDisplayName, context.Endpoint.DisplayName);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -89,13 +89,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint = CreateEndpoint("/hello", httpMethods: new string[] { "GeT", });
|
||||
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET");
|
||||
var (httpContext, context) = CreateContext("/hello", "GET");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -105,13 +105,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint = CreateEndpoint("/hello", httpMethods: new string[] { "GeT", }, acceptCorsPreflight: true);
|
||||
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET", corsPreflight: true);
|
||||
var (httpContext, context) = CreateContext("/hello", "GET", corsPreflight: true);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -121,13 +121,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint = CreateEndpoint("/hello");
|
||||
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET");
|
||||
var (httpContext, context) = CreateContext("/hello", "GET");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -137,13 +137,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint = CreateEndpoint("/hello", acceptCorsPreflight: true);
|
||||
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET", corsPreflight: true);
|
||||
var (httpContext, context) = CreateContext("/hello", "GET", corsPreflight: true);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Fact] // This matches because the endpoint accepts OPTIONS
|
||||
|
|
@ -153,13 +153,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint = CreateEndpoint("/hello", acceptCorsPreflight: false);
|
||||
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET", corsPreflight: true);
|
||||
var (httpContext, context) = CreateContext("/hello", "GET", corsPreflight: true);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -169,13 +169,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint = CreateEndpoint("/hello", httpMethods: new string[] { });
|
||||
|
||||
var matcher = CreateMatcher(endpoint);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET");
|
||||
var (httpContext, context) = CreateContext("/hello", "GET");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Fact] // When all of the candidates handles specific verbs, use a 405 endpoint
|
||||
|
|
@ -186,19 +186,19 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint2 = CreateEndpoint("/hello", httpMethods: new string[] { "DELETE" });
|
||||
|
||||
var matcher = CreateMatcher(endpoint1, endpoint2);
|
||||
var (httpContext, feature) = CreateContext("/hello", "POST");
|
||||
var (httpContext, context) = CreateContext("/hello", "POST");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
Assert.NotSame(endpoint1, feature.Endpoint);
|
||||
Assert.NotSame(endpoint2, feature.Endpoint);
|
||||
Assert.NotSame(endpoint1, context.Endpoint);
|
||||
Assert.NotSame(endpoint2, context.Endpoint);
|
||||
|
||||
Assert.Same(HttpMethodMatcherPolicy.Http405EndpointDisplayName, feature.Endpoint.DisplayName);
|
||||
Assert.Same(HttpMethodMatcherPolicy.Http405EndpointDisplayName, context.Endpoint.DisplayName);
|
||||
|
||||
// Invoke the endpoint
|
||||
await feature.Endpoint.RequestDelegate(httpContext);
|
||||
await context.Endpoint.RequestDelegate(httpContext);
|
||||
Assert.Equal(405, httpContext.Response.StatusCode);
|
||||
Assert.Equal("DELETE, GET, PUT", httpContext.Response.Headers["Allow"]);
|
||||
}
|
||||
|
|
@ -211,13 +211,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint2 = CreateEndpoint("/hello", httpMethods: new string[] { "DELETE" });
|
||||
|
||||
var matcher = CreateMatcher(endpoint1, endpoint2);
|
||||
var (httpContext, feature) = CreateContext("/hello", "POST", corsPreflight: true);
|
||||
var (httpContext, context) = CreateContext("/hello", "POST", corsPreflight: true);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
}
|
||||
|
||||
[Fact] // When one of the candidates handles all verbs, dont use a 405 endpoint
|
||||
|
|
@ -228,13 +228,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint2 = CreateEndpoint("/hello", httpMethods: new string[] { "DELETE" });
|
||||
|
||||
var matcher = CreateMatcher(endpoint1, endpoint2);
|
||||
var (httpContext, feature) = CreateContext("/hello", "POST");
|
||||
var (httpContext, context) = CreateContext("/hello", "POST");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -245,13 +245,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint2 = CreateEndpoint("/bar");
|
||||
|
||||
var matcher = CreateMatcher(endpoint1, endpoint2);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET");
|
||||
var (httpContext, context) = CreateContext("/hello", "GET");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint1);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint1);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -262,13 +262,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint2 = CreateEndpoint("/bar", httpMethods: new string[] { });
|
||||
|
||||
var matcher = CreateMatcher(endpoint1, endpoint2);
|
||||
var (httpContext, feature) = CreateContext("/hello", "GET");
|
||||
var (httpContext, context) = CreateContext("/hello", "GET");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint1);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint1);
|
||||
}
|
||||
|
||||
[Fact] // The non-http-method-specific endpoint is part of the same candidate set
|
||||
|
|
@ -279,13 +279,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
var endpoint2 = CreateEndpoint("/{x}", httpMethods: new string[] { });
|
||||
|
||||
var matcher = CreateMatcher(endpoint1, endpoint2);
|
||||
var (httpContext, feature) = CreateContext("/hello", "POST");
|
||||
var (httpContext, context) = CreateContext("/hello", "POST");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint2, ignoreValues: true);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint2, ignoreValues: true);
|
||||
}
|
||||
|
||||
private static Matcher CreateMatcher(params RouteEndpoint[] endpoints)
|
||||
|
|
@ -305,7 +305,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
return builder.Build();
|
||||
}
|
||||
|
||||
internal static (HttpContext httpContext, EndpointFeature feature) CreateContext(
|
||||
internal static (HttpContext httpContext, EndpointSelectorContext context) CreateContext(
|
||||
string path,
|
||||
string httpMethod,
|
||||
bool corsPreflight = false)
|
||||
|
|
@ -320,11 +320,11 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
httpContext.Request.Headers[AccessControlRequestMethod] = httpMethod;
|
||||
}
|
||||
|
||||
var feature = new EndpointFeature();
|
||||
httpContext.Features.Set<IEndpointFeature>(feature);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(feature);
|
||||
var context = new EndpointSelectorContext();
|
||||
httpContext.Features.Set<IEndpointFeature>(context);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(context);
|
||||
|
||||
return (httpContext, feature);
|
||||
return (httpContext, context);
|
||||
}
|
||||
internal static RouteEndpoint CreateEndpoint(
|
||||
string template,
|
||||
|
|
|
|||
|
|
@ -12,22 +12,22 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
internal static class MatcherAssert
|
||||
{
|
||||
public static void AssertMatch(EndpointFeature feature, HttpContext context, Endpoint expected)
|
||||
public static void AssertMatch(EndpointSelectorContext context, HttpContext httpContext, Endpoint expected)
|
||||
{
|
||||
AssertMatch(feature, context, expected, new RouteValueDictionary());
|
||||
AssertMatch(context, httpContext, expected, new RouteValueDictionary());
|
||||
}
|
||||
|
||||
public static void AssertMatch(EndpointFeature feature, HttpContext context, Endpoint expected, bool ignoreValues)
|
||||
public static void AssertMatch(EndpointSelectorContext context, HttpContext httpContext, Endpoint expected, bool ignoreValues)
|
||||
{
|
||||
AssertMatch(feature, context, expected, new RouteValueDictionary(), ignoreValues);
|
||||
AssertMatch(context, httpContext, expected, new RouteValueDictionary(), ignoreValues);
|
||||
}
|
||||
|
||||
public static void AssertMatch(EndpointFeature feature, HttpContext context, Endpoint expected, object values)
|
||||
public static void AssertMatch(EndpointSelectorContext context, HttpContext httpContext, Endpoint expected, object values)
|
||||
{
|
||||
AssertMatch(feature, context, expected, new RouteValueDictionary(values));
|
||||
AssertMatch(context, httpContext, expected, new RouteValueDictionary(values));
|
||||
}
|
||||
|
||||
public static void AssertMatch(EndpointFeature feature, HttpContext context, Endpoint expected, string[] keys, string[] values)
|
||||
public static void AssertMatch(EndpointSelectorContext context, HttpContext httpContext, Endpoint expected, string[] keys, string[] values)
|
||||
{
|
||||
keys = keys ?? Array.Empty<string>();
|
||||
values = values ?? Array.Empty<string>();
|
||||
|
|
@ -38,33 +38,33 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
}
|
||||
|
||||
var zipped = keys.Zip(values, (k, v) => new KeyValuePair<string, object>(k, v));
|
||||
AssertMatch(feature, context, expected, new RouteValueDictionary(zipped));
|
||||
AssertMatch(context, httpContext, expected, new RouteValueDictionary(zipped));
|
||||
}
|
||||
|
||||
public static void AssertMatch(
|
||||
EndpointFeature feature,
|
||||
HttpContext context,
|
||||
EndpointSelectorContext context,
|
||||
HttpContext httpContext,
|
||||
Endpoint expected,
|
||||
RouteValueDictionary values,
|
||||
bool ignoreValues = false)
|
||||
{
|
||||
if (feature.Endpoint == null)
|
||||
if (context.Endpoint == null)
|
||||
{
|
||||
throw new XunitException($"Was expected to match '{expected.DisplayName}' but did not match.");
|
||||
}
|
||||
|
||||
var actualValues = context.Features.Get<IRouteValuesFeature>().RouteValues;
|
||||
var actualValues = httpContext.Features.Get<IRouteValuesFeature>().RouteValues;
|
||||
|
||||
if (actualValues == null)
|
||||
{
|
||||
throw new XunitException("RouteValues is null.");
|
||||
}
|
||||
|
||||
if (!object.ReferenceEquals(expected, feature.Endpoint))
|
||||
if (!object.ReferenceEquals(expected, context.Endpoint))
|
||||
{
|
||||
throw new XunitException(
|
||||
$"Was expected to match '{expected.DisplayName}' but matched " +
|
||||
$"'{feature.Endpoint.DisplayName}' with values: {FormatRouteValues(actualValues)}.");
|
||||
$"'{context.Endpoint.DisplayName}' with values: {FormatRouteValues(actualValues)}.");
|
||||
}
|
||||
|
||||
if (!ignoreValues)
|
||||
|
|
@ -81,13 +81,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
}
|
||||
}
|
||||
|
||||
public static void AssertNotMatch(EndpointFeature feature, HttpContext context)
|
||||
public static void AssertNotMatch(EndpointSelectorContext context, HttpContext httpContext)
|
||||
{
|
||||
if (feature.Endpoint != null)
|
||||
if (context.Endpoint != null)
|
||||
{
|
||||
throw new XunitException(
|
||||
$"Was expected not to match '{feature.Endpoint.DisplayName}' " +
|
||||
$"but matched with values: {FormatRouteValues(context.Features.Get<IRouteValuesFeature>().RouteValues)}.");
|
||||
$"Was expected not to match '{context.Endpoint.DisplayName}' " +
|
||||
$"but matched with values: {FormatRouteValues(httpContext.Features.Get<IRouteValuesFeature>().RouteValues)}.");
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -13,13 +13,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher("/");
|
||||
var (httpContext, feature) = CreateContext("/");
|
||||
var (httpContext, context) = CreateContext("/");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -27,13 +27,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher("/simple");
|
||||
var (httpContext, feature) = CreateContext("/simple");
|
||||
var (httpContext, context) = CreateContext("/simple");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -41,13 +41,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher("/simple");
|
||||
var (httpContext, feature) = CreateContext("/simple/");
|
||||
var (httpContext, context) = CreateContext("/simple/");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -58,13 +58,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher("/Simple");
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
// Some matchers will optimize for the ASCII case
|
||||
|
|
@ -75,13 +75,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
// Matchers should operate on the decoded representation - a matcher that calls
|
||||
|
|
@ -93,13 +93,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -113,13 +113,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher("/simple");
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -130,13 +130,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext("/simple");
|
||||
var (httpContext, context) = CreateContext("/simple");
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
// Matchers do their own 'splitting' of the path into segments, so including
|
||||
|
|
@ -153,13 +153,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint);
|
||||
}
|
||||
|
||||
// Matchers do their own 'splitting' of the path into segments, so including
|
||||
|
|
@ -184,13 +184,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -198,14 +198,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher("/{p}");
|
||||
var (httpContext, feature) = CreateContext("/14");
|
||||
var (httpContext, context) = CreateContext("/14");
|
||||
var values = new RouteValueDictionary(new { p = "14", });
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, values);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -213,14 +213,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher("/{p:int}");
|
||||
var (httpContext, feature) = CreateContext("/14");
|
||||
var (httpContext, context) = CreateContext("/14");
|
||||
var values = new RouteValueDictionary(new { p = "14", });
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, values);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -228,14 +228,14 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher("/{p}");
|
||||
var (httpContext, feature) = CreateContext("/14/");
|
||||
var (httpContext, context) = CreateContext("/14/");
|
||||
var values = new RouteValueDictionary(new { p = "14", });
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, values);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
|
|
@ -243,7 +243,7 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher("/foo/{ }/{.!$%}/{dynamic.data}");
|
||||
var (httpContext, feature) = CreateContext("/foo/space/weirdmatch/matcherid");
|
||||
var (httpContext, context) = CreateContext("/foo/space/weirdmatch/matcherid");
|
||||
var values = new RouteValueDictionary()
|
||||
{
|
||||
{ " ", "space" },
|
||||
|
|
@ -252,10 +252,10 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
};
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, values);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -267,13 +267,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher("/{p}");
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -288,13 +288,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertMatch(feature, httpContext, endpoint, keys, values);
|
||||
MatcherAssert.AssertMatch(context, httpContext, endpoint, keys, values);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
|
|
@ -317,13 +317,13 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
// Arrange
|
||||
var (matcher, endpoint) = CreateMatcher(template);
|
||||
var (httpContext, feature) = CreateContext(path);
|
||||
var (httpContext, context) = CreateContext(path);
|
||||
|
||||
// Act
|
||||
await matcher.MatchAsync(httpContext, feature);
|
||||
await matcher.MatchAsync(httpContext, context);
|
||||
|
||||
// Assert
|
||||
MatcherAssert.AssertNotMatch(feature, httpContext);
|
||||
MatcherAssert.AssertNotMatch(context, httpContext);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -14,18 +14,18 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
{
|
||||
internal abstract Matcher CreateMatcher(params RouteEndpoint[] endpoints);
|
||||
|
||||
internal static (HttpContext httpContext, EndpointFeature feature) CreateContext(string path)
|
||||
internal static (HttpContext httpContext, EndpointSelectorContext context) CreateContext(string path)
|
||||
{
|
||||
var httpContext = new DefaultHttpContext();
|
||||
httpContext.Request.Method = "TEST";
|
||||
httpContext.Request.Path = path;
|
||||
httpContext.RequestServices = CreateServices();
|
||||
|
||||
var feature = new EndpointFeature();
|
||||
httpContext.Features.Set<IEndpointFeature>(feature);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(feature);
|
||||
var context = new EndpointSelectorContext();
|
||||
httpContext.Features.Set<IEndpointFeature>(context);
|
||||
httpContext.Features.Set<IRouteValuesFeature>(context);
|
||||
|
||||
return (httpContext, feature);
|
||||
return (httpContext, context);
|
||||
}
|
||||
|
||||
// The older routing implementations retrieve services when they first execute.
|
||||
|
|
|
|||
|
|
@ -4,7 +4,6 @@
|
|||
using System;
|
||||
using System.Threading.Tasks;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.AspNetCore.Http.Features;
|
||||
|
||||
namespace Microsoft.AspNetCore.Routing.Matching
|
||||
{
|
||||
|
|
@ -18,25 +17,25 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
_inner = inner;
|
||||
}
|
||||
|
||||
public async override Task MatchAsync(HttpContext httpContext, EndpointFeature feature)
|
||||
public async override Task MatchAsync(HttpContext httpContext, EndpointSelectorContext context)
|
||||
{
|
||||
if (httpContext == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(httpContext));
|
||||
}
|
||||
|
||||
if (feature == null)
|
||||
if (context == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(feature));
|
||||
throw new ArgumentNullException(nameof(context));
|
||||
}
|
||||
|
||||
var context = new RouteContext(httpContext);
|
||||
await _inner.RouteAsync(context);
|
||||
var routeContext = new RouteContext(httpContext);
|
||||
await _inner.RouteAsync(routeContext);
|
||||
|
||||
if (context.Handler != null)
|
||||
if (routeContext.Handler != null)
|
||||
{
|
||||
feature.RouteValues = context.RouteData.Values;
|
||||
await context.Handler(httpContext);
|
||||
context.RouteValues = routeContext.RouteData.Values;
|
||||
await routeContext.Handler(httpContext);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -91,18 +91,18 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public async Task RouteAsync(RouteContext context)
|
||||
public async Task RouteAsync(RouteContext routeContext)
|
||||
{
|
||||
var feature = (EndpointFeature)context.HttpContext.Features.Get<IEndpointFeature>();
|
||||
var context = (EndpointSelectorContext)routeContext.HttpContext.Features.Get<IEndpointFeature>();
|
||||
|
||||
// This is needed due to a quirk of our tests - they reuse the endpoint feature
|
||||
// across requests.
|
||||
feature.Endpoint = null;
|
||||
context.Endpoint = null;
|
||||
|
||||
await _selector.SelectAsync(context.HttpContext, feature, new CandidateSet(_candidates, _scores));
|
||||
if (feature.Endpoint != null)
|
||||
await _selector.SelectAsync(routeContext.HttpContext, context, new CandidateSet(_candidates, _scores));
|
||||
if (context.Endpoint != null)
|
||||
{
|
||||
context.Handler = (_) => Task.CompletedTask;
|
||||
routeContext.Handler = (_) => Task.CompletedTask;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -19,25 +19,25 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
_inner = inner;
|
||||
}
|
||||
|
||||
public async override Task MatchAsync(HttpContext httpContext, EndpointFeature feature)
|
||||
public async override Task MatchAsync(HttpContext httpContext, EndpointSelectorContext context)
|
||||
{
|
||||
if (httpContext == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(httpContext));
|
||||
}
|
||||
|
||||
if (feature == null)
|
||||
if (context == null)
|
||||
{
|
||||
throw new ArgumentNullException(nameof(feature));
|
||||
throw new ArgumentNullException(nameof(context));
|
||||
}
|
||||
|
||||
var context = new RouteContext(httpContext);
|
||||
await _inner.RouteAsync(context);
|
||||
var routeContext = new RouteContext(httpContext);
|
||||
await _inner.RouteAsync(routeContext);
|
||||
|
||||
if (context.Handler != null)
|
||||
if (routeContext.Handler != null)
|
||||
{
|
||||
feature.RouteValues = context.RouteData.Values;
|
||||
await context.Handler(httpContext);
|
||||
context.RouteValues = routeContext.RouteData.Values;
|
||||
await routeContext.Handler(httpContext);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -93,17 +93,17 @@ namespace Microsoft.AspNetCore.Routing.Matching
|
|||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public async Task RouteAsync(RouteContext context)
|
||||
public async Task RouteAsync(RouteContext routeContext)
|
||||
{
|
||||
var feature = (EndpointFeature)context.HttpContext.Features.Get<IEndpointFeature>();
|
||||
var context = (EndpointSelectorContext)routeContext.HttpContext.Features.Get<IEndpointFeature>();
|
||||
|
||||
// This is needed due to a quirk of our tests - they reuse the endpoint feature.
|
||||
feature.Endpoint = null;
|
||||
context.Endpoint = null;
|
||||
|
||||
await _selector.SelectAsync(context.HttpContext, feature, new CandidateSet(_candidates, _scores));
|
||||
if (feature.Endpoint != null)
|
||||
await _selector.SelectAsync(routeContext.HttpContext, context, new CandidateSet(_candidates, _scores));
|
||||
if (context.Endpoint != null)
|
||||
{
|
||||
context.Handler = (_) => Task.CompletedTask;
|
||||
routeContext.Handler = (_) => Task.CompletedTask;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -17,12 +17,12 @@ namespace Microsoft.AspNetCore.Routing.TestObjects
|
|||
_isHandled = isHandled;
|
||||
}
|
||||
|
||||
public override Task MatchAsync(HttpContext httpContext, EndpointFeature feature)
|
||||
public override Task MatchAsync(HttpContext httpContext, EndpointSelectorContext context)
|
||||
{
|
||||
if (_isHandled)
|
||||
{
|
||||
feature.RouteValues = new RouteValueDictionary(new { controller = "Home", action = "Index" });
|
||||
feature.Endpoint = new Endpoint(TestConstants.EmptyRequestDelegate, EndpointMetadataCollection.Empty, "Test endpoint");
|
||||
context.RouteValues = new RouteValueDictionary(new { controller = "Home", action = "Index" });
|
||||
context.Endpoint = new Endpoint(TestConstants.EmptyRequestDelegate, EndpointMetadataCollection.Empty, "Test endpoint");
|
||||
}
|
||||
|
||||
return Task.CompletedTask;
|
||||
|
|
|
|||
Loading…
Reference in New Issue