Adding Tests for InlineRouting Support.
This commit is contained in:
parent
2e96ba5862
commit
5dc8267920
|
|
@ -1,8 +1,7 @@
|
|||
using System.Text.RegularExpressions;
|
||||
using Microsoft.AspNet;
|
||||
using Microsoft.AspNet.Builder;
|
||||
using Microsoft.AspNet.Http;
|
||||
using Microsoft.AspNet.Routing;
|
||||
using Microsoft.AspNet.Routing.Constraints;
|
||||
|
||||
namespace RoutingSample.Web
|
||||
{
|
||||
|
|
|
|||
|
|
@ -24,6 +24,7 @@
|
|||
<Compile Include="BuilderExtensions.cs" />
|
||||
<Compile Include="Constraints\CompositeRouteConstraint.cs" />
|
||||
<Compile Include="Constraints\IntRouteConstraint.cs" />
|
||||
<Compile Include="Constraints\RegexConstraint.cs" />
|
||||
<Compile Include="DefaultInlineConstraintResolver.cs" />
|
||||
<Compile Include="IInlineConstraintResolver.cs" />
|
||||
<Compile Include="INamedRouter.cs" />
|
||||
|
|
@ -33,7 +34,6 @@
|
|||
<Compile Include="IRouter.cs" />
|
||||
<Compile Include="NotNullAttribute.cs" />
|
||||
<Compile Include="Properties\Resources.Designer.cs" />
|
||||
<Compile Include="RegexConstraint.cs" />
|
||||
<Compile Include="RouteCollection.cs" />
|
||||
<Compile Include="RouteCollectionExtensions.cs" />
|
||||
<Compile Include="RouteConstraintBuilder.cs" />
|
||||
|
|
@ -52,4 +52,4 @@
|
|||
<Compile Include="VirtualPathContext.cs" />
|
||||
</ItemGroup>
|
||||
<Import Project="$(VSToolsPath)\AspNet\Microsoft.Web.AspNet.targets" Condition="'$(VSToolsPath)' != ''" />
|
||||
</Project>
|
||||
</Project>
|
||||
|
|
@ -196,10 +196,6 @@ namespace Microsoft.AspNet.Routing.Template
|
|||
context.Error = Resources.TemplateRoute_OptionalCannotHaveDefaultValue;
|
||||
return false;
|
||||
}
|
||||
// A workaround is to add it as a separate entry in the defaults argument.
|
||||
context.Error = Resources.TemplateRoute_OptionalCannotHaveDefaultValue;
|
||||
return false;
|
||||
}
|
||||
|
||||
var parameterName = templatePart.Name;
|
||||
if (IsValidParameterName(context, parameterName))
|
||||
|
|
|
|||
|
|
@ -43,13 +43,13 @@ namespace Microsoft.AspNet.Routing.Template
|
|||
_routeTemplate = routeTemplate ?? string.Empty;
|
||||
Name = routeName;
|
||||
_defaults = defaults ?? new Dictionary<string, object>(StringComparer.OrdinalIgnoreCase);
|
||||
_constraints = RouteConstraintBuilder.BuildConstraints(constraints, _routeTemplate) ??
|
||||
_constraints = RouteConstraintBuilder.BuildConstraints(constraints, _routeTemplate) ??
|
||||
new Dictionary<string, IRouteConstraint>();
|
||||
|
||||
// The parser will throw for invalid routes.
|
||||
_parsedTemplate = TemplateParser.Parse(RouteTemplate, inlineConstraintResolver);
|
||||
UpdateInlineDefaultValuesAndConstraints();
|
||||
|
||||
|
||||
_matcher = new TemplateMatcher(_parsedTemplate);
|
||||
_binder = new TemplateBinder(_parsedTemplate, _defaults);
|
||||
}
|
||||
|
|
@ -184,14 +184,13 @@ namespace Microsoft.AspNet.Routing.Template
|
|||
IRouteConstraint constraint;
|
||||
if (_constraints.TryGetValue(parameter.Name, out constraint))
|
||||
{
|
||||
_constraints[parameter.Name] =
|
||||
new CompositeRouteConstraint(new []{ constraint, parameter.InlineConstraint });
|
||||
_constraints[parameter.Name] =
|
||||
new CompositeRouteConstraint(new[] { constraint, parameter.InlineConstraint });
|
||||
}
|
||||
else
|
||||
{
|
||||
_constraints[parameter.Name] = parameter.InlineConstraint;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (parameter.DefaultValue != null)
|
||||
|
|
@ -210,4 +209,4 @@ namespace Microsoft.AspNet.Routing.Template
|
|||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,81 @@
|
|||
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using Microsoft.AspNet.Http;
|
||||
using Microsoft.AspNet.Routing.Constraints;
|
||||
using Xunit;
|
||||
|
||||
namespace Microsoft.AspNet.Routing.Tests
|
||||
{
|
||||
public class DefaultInlineConstraintResolverTest
|
||||
{
|
||||
[Fact]
|
||||
public void ResolveConstraint_IntConstraint_ResolvesCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var constraint = new DefaultInlineConstraintResolver().ResolveConstraint("int");
|
||||
|
||||
// Assert
|
||||
Assert.IsType<IntRouteConstraint>(constraint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ResolveConstraint_IntConstraintWithArgument_Throws()
|
||||
{
|
||||
// Act & Assert
|
||||
var ex = Assert.Throws<InvalidOperationException>(
|
||||
() => new DefaultInlineConstraintResolver().ResolveConstraint("int(5)"));
|
||||
Assert.Equal("Could not find a constructor for constraint type 'IntRouteConstraint'"+
|
||||
" with the following number of parameters: 1.",
|
||||
ex.Message);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ResolveConstraint_SupportsCustomConstraints()
|
||||
{
|
||||
// Arrange
|
||||
var resolver = new DefaultInlineConstraintResolver();
|
||||
resolver.ConstraintMap.Add("custom", typeof(CustomRouteConstraint));
|
||||
|
||||
// Act
|
||||
var constraint = resolver.ResolveConstraint("custom(argument)");
|
||||
|
||||
// Assert
|
||||
Assert.IsType<CustomRouteConstraint>(constraint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ResolveConstraint_CustomConstraintThatDoesNotImplementIRouteConstraint_Throws()
|
||||
{
|
||||
// Arrange
|
||||
var resolver = new DefaultInlineConstraintResolver();
|
||||
resolver.ConstraintMap.Add("custom", typeof(string));
|
||||
|
||||
// Act & Assert
|
||||
var ex = Assert.Throws<InvalidOperationException>(() => resolver.ResolveConstraint("custom"));
|
||||
Assert.Equal("The constraint type 'System.String' which is mapped to constraint key 'custom'"+
|
||||
" must implement the 'IRouteConstraint' interface.",
|
||||
ex.Message);
|
||||
}
|
||||
|
||||
private class CustomRouteConstraint : IRouteConstraint
|
||||
{
|
||||
public CustomRouteConstraint(string pattern)
|
||||
{
|
||||
Pattern = pattern;
|
||||
}
|
||||
|
||||
public string Pattern { get; private set; }
|
||||
public bool Match(HttpContext httpContext,
|
||||
IRouter route,
|
||||
string routeKey,
|
||||
IDictionary<string, object> values,
|
||||
RouteDirection routeDirection)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,304 @@
|
|||
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using Microsoft.AspNet.Http;
|
||||
using Microsoft.AspNet.Routing.Constraints;
|
||||
using Microsoft.AspNet.Routing.Template;
|
||||
using Xunit;
|
||||
|
||||
namespace Microsoft.AspNet.Routing.Tests
|
||||
{
|
||||
public class InlineRouteParameterParserTests
|
||||
{
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintAndDefault_ParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter("param:int=111111");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.Equal("111111", templatePart.DefaultValue);
|
||||
Assert.IsType<IntRouteConstraint>(templatePart.InlineConstraint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintWithArgumentsAndDefault_ParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:test(\d+)=111111");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.Equal("111111", templatePart.DefaultValue);
|
||||
Assert.IsType<TestRouteConstraint>(templatePart.InlineConstraint);
|
||||
Assert.Equal(@"\d+", ((TestRouteConstraint)templatePart.InlineConstraint).Pattern);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintAndOptional_ParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:int?");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.True(templatePart.IsOptional);
|
||||
Assert.IsType<IntRouteConstraint>(templatePart.InlineConstraint);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintWithArgumentsAndOptional_ParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:test(\d+)?");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.True(templatePart.IsOptional);
|
||||
Assert.Equal(@"\d+", ((TestRouteConstraint)templatePart.InlineConstraint).Pattern);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ChainedConstraints_ParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:test(\d+):test(\w+)");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.IsType<CompositeRouteConstraint>(templatePart.InlineConstraint);
|
||||
var constraint = (CompositeRouteConstraint)templatePart.InlineConstraint;
|
||||
Assert.Equal(@"\d+", ((TestRouteConstraint)constraint.Constraints.ElementAt(0)).Pattern);
|
||||
Assert.Equal(@"\w+", ((TestRouteConstraint)constraint.Constraints.ElementAt(1)).Pattern);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteTemplate_ConstraintsDefaultsAndOptionalsInMultipleSections_ParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var template = ParseRouteTemplate(@"some/url-{p1:int:test(3)=hello}/{p2=abc}/{p3?}");
|
||||
|
||||
// Assert
|
||||
var parameters = template.Parameters.ToArray();
|
||||
|
||||
var param1 = parameters[0];
|
||||
Assert.Equal("p1", param1.Name);
|
||||
Assert.Equal("hello", param1.DefaultValue);
|
||||
Assert.False(param1.IsOptional);
|
||||
Assert.IsType<CompositeRouteConstraint>(param1.InlineConstraint);
|
||||
var constraint = (CompositeRouteConstraint)param1.InlineConstraint;
|
||||
Assert.IsType<IntRouteConstraint>(constraint.Constraints.ElementAt(0));
|
||||
Assert.IsType<TestRouteConstraint>(constraint.Constraints.ElementAt(1));
|
||||
|
||||
var param2 = parameters[1];
|
||||
Assert.Equal("p2", param2.Name);
|
||||
Assert.Equal("abc", param2.DefaultValue);
|
||||
Assert.False(param2.IsOptional);
|
||||
|
||||
var param3 = parameters[2];
|
||||
Assert.Equal("p3", param3.Name);
|
||||
Assert.True(param3.IsOptional);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_NoTokens_ParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter("world");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("world", templatePart.Name);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ParamDefault_ParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter("param=world");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.Equal("world", templatePart.DefaultValue);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintWithClosingBraceInPattern_ClosingBraceIsParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:test(\})");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.IsType<TestRouteConstraint>(templatePart.InlineConstraint);
|
||||
Assert.Equal(@"\}", ((TestRouteConstraint)templatePart.InlineConstraint).Pattern);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintWithClosingParenInPattern_ClosingParenIsParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:test(\))");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.IsType<TestRouteConstraint>(templatePart.InlineConstraint);
|
||||
Assert.Equal(@"\)", ((TestRouteConstraint)templatePart.InlineConstraint).Pattern);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintWithColonInPattern_ColonIsParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:test(:)");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.IsType<TestRouteConstraint>(templatePart.InlineConstraint);
|
||||
Assert.Equal(@":", ((TestRouteConstraint)templatePart.InlineConstraint).Pattern);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintWithCommaInPattern_PatternIsParsedCorrectly()
|
||||
{
|
||||
// Arrange
|
||||
var templatePart = ParseParameter(@"param:test(\w,\w)");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.IsType<TestRouteConstraint>(templatePart.InlineConstraint);
|
||||
Assert.Equal(@"\w,\w", ((TestRouteConstraint)templatePart.InlineConstraint).Pattern);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[InlineData(",")]
|
||||
[InlineData("(")]
|
||||
[InlineData(")")]
|
||||
[InlineData("}")]
|
||||
[InlineData("{")]
|
||||
public void ParseRouteParameter_MisplacedSpecialCharacterInParameter_Throws(string character)
|
||||
{
|
||||
// Arrange
|
||||
var unresolvedConstraint = character + @"test(\w,\w)";
|
||||
var parameter = "param:" + unresolvedConstraint;
|
||||
|
||||
// Act & Assert
|
||||
var ex = Assert.Throws<InvalidOperationException>(() => ParseParameter(parameter));
|
||||
Assert.Equal(@"The inline constraint resolver of type 'DefaultInlineConstraintResolver'"+
|
||||
" was unable to resolve the following inline constraint: '"+ unresolvedConstraint + "'.",
|
||||
ex.Message);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintWithEqualsSignInPattern_PatternIsParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:test(=)");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.Null(templatePart.DefaultValue);
|
||||
Assert.IsType<TestRouteConstraint>(templatePart.InlineConstraint);
|
||||
Assert.Equal(@"=", ((TestRouteConstraint)templatePart.InlineConstraint).Pattern);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintWithOpenBraceInPattern_PatternIsParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:test(\{)");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.IsType<TestRouteConstraint>(templatePart.InlineConstraint);
|
||||
Assert.Equal(@"\{", ((TestRouteConstraint)templatePart.InlineConstraint).Pattern);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintWithOpenParenInPattern_PatternIsParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:test(\()");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.IsType<TestRouteConstraint>(templatePart.InlineConstraint);
|
||||
Assert.Equal(@"\(", ((TestRouteConstraint)templatePart.InlineConstraint).Pattern);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void ParseRouteParameter_ConstraintWithQuestionMarkInPattern_PatternIsParsedCorrectly()
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(@"param:test(\?)");
|
||||
|
||||
// Assert
|
||||
Assert.Equal("param", templatePart.Name);
|
||||
Assert.Null(templatePart.DefaultValue);
|
||||
Assert.False(templatePart.IsOptional);
|
||||
Assert.IsType<TestRouteConstraint>(templatePart.InlineConstraint);
|
||||
Assert.Equal(@"\?", ((TestRouteConstraint)templatePart.InlineConstraint).Pattern);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[InlineData("", "")]
|
||||
[InlineData("?", "")]
|
||||
[InlineData("*", "")]
|
||||
[InlineData(" ", " ")]
|
||||
[InlineData("\t", "\t")]
|
||||
[InlineData("#!@#$%Q@#@%", "#!@#$%Q@#@%")]
|
||||
[InlineData(",,,", ",,,")]
|
||||
public void ParseRouteParameter_ParameterWithoutInlineConstraint_ReturnsTemplatePartWithEmptyInlineValues(
|
||||
string parameter,
|
||||
string expectedParameterName)
|
||||
{
|
||||
// Arrange & Act
|
||||
var templatePart = ParseParameter(parameter);
|
||||
|
||||
// Assert
|
||||
Assert.Equal(expectedParameterName, templatePart.Name);
|
||||
Assert.Null(templatePart.InlineConstraint);
|
||||
Assert.Null(templatePart.DefaultValue);
|
||||
}
|
||||
|
||||
|
||||
private TemplatePart ParseParameter(string routeParameter)
|
||||
{
|
||||
var constraintResolver = new DefaultInlineConstraintResolver();
|
||||
|
||||
// TODO: This will be removed once this is supported in product code.
|
||||
constraintResolver.ConstraintMap.Add("test", typeof(TestRouteConstraint));
|
||||
var templatePart = InlineRouteParameterParser.ParseRouteParameter(routeParameter, constraintResolver);
|
||||
return templatePart;
|
||||
}
|
||||
|
||||
private static Template.Template ParseRouteTemplate(string template)
|
||||
{
|
||||
var constraintResolver = new DefaultInlineConstraintResolver();
|
||||
|
||||
constraintResolver.ConstraintMap.Add("test", typeof(TestRouteConstraint));
|
||||
return TemplateParser.Parse(template, constraintResolver);
|
||||
}
|
||||
|
||||
private class TestRouteConstraint : IRouteConstraint
|
||||
{
|
||||
public TestRouteConstraint(string pattern)
|
||||
{
|
||||
Pattern = pattern;
|
||||
}
|
||||
|
||||
public string Pattern { get; private set; }
|
||||
public bool Match(HttpContext httpContext,
|
||||
IRouter route,
|
||||
string routeKey,
|
||||
IDictionary<string, object> values,
|
||||
RouteDirection routeDirection)
|
||||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -22,8 +22,11 @@
|
|||
<ItemGroup>
|
||||
<Compile Include="ConstraintMatcherTests.cs" />
|
||||
<Compile Include="ConstraintsBuilderTests.cs" />
|
||||
<Compile Include="DefaultInlineConstraintResolverTest.cs" />
|
||||
<Compile Include="RegexConstraintTests.cs" />
|
||||
<Compile Include="RouteCollectionTest.cs" />
|
||||
<Compile Include="InlineRouteParameterParserTests.cs" />
|
||||
<Compile Include="RouteConstraintsTests.cs" />
|
||||
<Compile Include="RouteValueDictionaryTests.cs" />
|
||||
<Compile Include="Template\TemplateBinderTests.cs" />
|
||||
<Compile Include="Template\TemplateMatcherTests.cs" />
|
||||
|
|
|
|||
|
|
@ -0,0 +1,97 @@
|
|||
// Copyright (c) Microsoft Open Technologies, Inc. All rights reserved.
|
||||
// Licensed under the Apache License, Version 2.0. See License.txt in the project root for license information.
|
||||
|
||||
#if NET45
|
||||
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq.Expressions;
|
||||
using Microsoft.AspNet.Http;
|
||||
using Microsoft.AspNet.Routing.Constraints;
|
||||
using Moq;
|
||||
using Xunit;
|
||||
|
||||
namespace Microsoft.AspNet.Routing.Tests
|
||||
{
|
||||
public class RouteConstraintsTests
|
||||
{
|
||||
[Theory]
|
||||
[InlineData(42, true)]
|
||||
[InlineData("42", true)]
|
||||
[InlineData(3.14, false)]
|
||||
[InlineData("43.567", false)]
|
||||
[InlineData("42a", false)]
|
||||
public void IntRouteConstraint_Match_AppliesConstraint(object parameterValue, bool expected)
|
||||
{
|
||||
// Arrange
|
||||
var constraint = new IntRouteConstraint();
|
||||
|
||||
// Act
|
||||
var actual = TestValue(constraint, parameterValue);
|
||||
|
||||
// Assert
|
||||
Assert.Equal(expected, actual);
|
||||
}
|
||||
|
||||
[Theory]
|
||||
[InlineData(true, true, true)]
|
||||
[InlineData(true, false, false)]
|
||||
[InlineData(false, true, false)]
|
||||
[InlineData(false, false, false)]
|
||||
public void CompoundRouteConstraint_Match_CallsMatchOnInnerConstraints(bool inner1Result,
|
||||
bool inner2Result,
|
||||
bool expected)
|
||||
{
|
||||
// Arrange
|
||||
var inner1 = MockConstraintWithResult(inner1Result);
|
||||
var inner2 = MockConstraintWithResult(inner2Result);
|
||||
|
||||
// Act
|
||||
var constraint = new CompositeRouteConstraint(new[] { inner1.Object, inner2.Object });
|
||||
var actual = TestValue(constraint, null);
|
||||
|
||||
// Assert
|
||||
Assert.Equal(expected, actual);
|
||||
}
|
||||
|
||||
static Expression<Func<IRouteConstraint, bool>> ConstraintMatchMethodExpression =
|
||||
c => c.Match(It.IsAny<HttpContext>(),
|
||||
It.IsAny<IRouter>(),
|
||||
It.IsAny<string>(),
|
||||
It.IsAny<Dictionary<string, object>>(),
|
||||
It.IsAny<RouteDirection>());
|
||||
|
||||
private static Mock<IRouteConstraint> MockConstraintWithResult(bool result)
|
||||
{
|
||||
var mock = new Mock<IRouteConstraint>();
|
||||
mock.Setup(ConstraintMatchMethodExpression)
|
||||
.Returns(result)
|
||||
.Verifiable();
|
||||
return mock;
|
||||
}
|
||||
|
||||
private static void AssertMatchWasCalled(Mock<IRouteConstraint> mock, Times times)
|
||||
{
|
||||
mock.Verify(ConstraintMatchMethodExpression, times);
|
||||
}
|
||||
|
||||
private static bool TestValue(IRouteConstraint constraint, object value, Action<IRouter> routeConfig = null)
|
||||
{
|
||||
var context = new Mock<HttpContext>();
|
||||
|
||||
IRouter route = new RouteCollection();
|
||||
|
||||
if (routeConfig != null)
|
||||
{
|
||||
routeConfig(route);
|
||||
}
|
||||
|
||||
var parameterName = "fake";
|
||||
var values = new Dictionary<string, object>() { { parameterName, value } };
|
||||
var routeDirection = RouteDirection.IncomingRequest;
|
||||
return constraint.Match(context.Object, route, parameterName, values, routeDirection);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif
|
||||
|
|
@ -4,6 +4,7 @@
|
|||
#if NET45
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Microsoft.AspNet.Http;
|
||||
using Microsoft.AspNet.Routing.Constraints;
|
||||
|
|
@ -425,6 +426,49 @@ namespace Microsoft.AspNet.Routing.Template.Tests
|
|||
Assert.Equal(mockConstraint, constraints["action"]);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RegisteringRouteWithOneInlineConstraintAndOneUsingConstraintArgument()
|
||||
{
|
||||
// Arrange
|
||||
var collection = new RouteCollection();
|
||||
collection.DefaultHandler = new Mock<IRouter>().Object;
|
||||
collection.InlineConstraintResolver = new DefaultInlineConstraintResolver();
|
||||
|
||||
collection.MapRoute("mockName",
|
||||
"{controller}/{action}/{id:int}",
|
||||
defaults: null,
|
||||
constraints: new { id = "1*" });
|
||||
|
||||
var constraints = ((TemplateRoute)collection[0]).Constraints;
|
||||
|
||||
// Assert
|
||||
Assert.Equal(1, constraints.Count);
|
||||
var constraint = (CompositeRouteConstraint)constraints["id"];
|
||||
Assert.IsType<CompositeRouteConstraint>(constraint);
|
||||
Assert.IsType<RegexConstraint>(constraint.Constraints.ElementAt(0));
|
||||
Assert.IsType<IntRouteConstraint>(constraint.Constraints.ElementAt(1));
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RegisteringRoute_WithOneInlineConstraint_AddsItToConstraintCollection()
|
||||
{
|
||||
// Arrange
|
||||
var collection = new RouteCollection();
|
||||
collection.DefaultHandler = new Mock<IRouter>().Object;
|
||||
collection.InlineConstraintResolver = new DefaultInlineConstraintResolver();
|
||||
|
||||
collection.MapRoute("mockName",
|
||||
"{controller}/{action}/{id:int}",
|
||||
defaults: null,
|
||||
constraints: null);
|
||||
|
||||
var constraints = ((TemplateRoute)collection[0]).Constraints;
|
||||
|
||||
// Assert
|
||||
Assert.Equal(1, constraints.Count);
|
||||
Assert.IsType<IntRouteConstraint>(constraints["id"]);
|
||||
}
|
||||
|
||||
[Fact]
|
||||
public void RegisteringRouteWithRouteName_WithNullDefaults_AddsTheRoute()
|
||||
{
|
||||
|
|
|
|||
Loading…
Reference in New Issue