public void FindTryParseStringMethod_ReturnsTheExpectedTryParseMethodWithInvariantCultureDateType(Type type) { var methodFound = new ParameterBindingMethodCache().FindTryParseMethod(@type); Assert.NotNull(methodFound); var call = methodFound !(Expression.Variable(type, "parsedValue"), Expression.Constant(CultureInfo.InvariantCulture)) as MethodCallExpression; Assert.NotNull(call); var parameters = call !.Method.GetParameters(); if (@type == typeof(TimeSpan)) { Assert.Equal(3, parameters.Length); Assert.Equal(typeof(string), parameters[0].ParameterType); Assert.Equal(typeof(IFormatProvider), parameters[1].ParameterType); Assert.True(parameters[2].IsOut); } else { Assert.Equal(4, parameters.Length); Assert.Equal(typeof(string), parameters[0].ParameterType); Assert.Equal(typeof(IFormatProvider), parameters[1].ParameterType); Assert.Equal(typeof(DateTimeStyles), parameters[2].ParameterType); Assert.True(parameters[3].IsOut); } }
public async Task FindBindAsyncMethod_FindsSingleArgBindAsync() { var type = typeof(BindAsyncSingleArgStruct); var cache = new ParameterBindingMethodCache(); var parameter = new MockParameterInfo(type, "bindAsyncSingleArgStruct"); var methodFound = cache.FindBindAsyncMethod(parameter); Assert.NotNull(methodFound.Expression); Assert.Equal(1, methodFound.ParamCount); var parsedValue = Expression.Variable(type, "parsedValue"); var parseHttpContext = Expression.Lambda <Func <HttpContext, ValueTask <object> > >( Expression.Block(new[] { parsedValue }, methodFound.Expression !), ParameterBindingMethodCache.HttpContextExpr).Compile(); var httpContext = new DefaultHttpContext { Request = { Headers = { ["ETag"] = "42", }, }, }; Assert.Equal(new BindAsyncSingleArgStruct(42), await parseHttpContext(httpContext)); }
public void FindBindAsyncMethod_IgnoresInvalidBindAsyncIfGoodOneFound(Type type) { var cache = new ParameterBindingMethodCache(); var parameter = new MockParameterInfo(type, "anything"); var(expression, _) = cache.FindBindAsyncMethod(parameter); Assert.NotNull(expression); }
public void FindBindAsyncMethod_ThrowsIfMultipleInterfacesMatch() { var cache = new ParameterBindingMethodCache(); var parameter = new MockParameterInfo(typeof(BindAsyncFromMultipleInterfaces), "anything"); var ex = Assert.Throws <InvalidOperationException>(() => cache.FindBindAsyncMethod(parameter)); Assert.Equal("BindAsyncFromMultipleInterfaces implements multiple interfaces defining a static System.Threading.Tasks.ValueTask`1[Microsoft.AspNetCore.Http.Extensions.Tests.ParameterBindingMethodCacheTests+BindAsyncFromMultipleInterfaces] BindAsync(Microsoft.AspNetCore.Http.HttpContext) method causing ambiguity.", ex.Message); }
public void FindBindAsyncMethod_ThrowsIfInvalidBindAsyncOnType(Type type) { var cache = new ParameterBindingMethodCache(); var parameter = new MockParameterInfo(type, "anything"); var ex = Assert.Throws <InvalidOperationException>( () => cache.FindBindAsyncMethod(parameter)); Assert.StartsWith($"BindAsync method found on {TypeNameHelper.GetTypeDisplayName(type, fullName: false)} with incorrect format. Must be a static method with format", ex.Message); Assert.Contains($"ValueTask<{TypeNameHelper.GetTypeDisplayName(type, fullName: false)}> BindAsync(HttpContext context, ParameterInfo parameter)", ex.Message); Assert.Contains($"ValueTask<{TypeNameHelper.GetTypeDisplayName(type, fullName: false)}> BindAsync(HttpContext context)", ex.Message); Assert.Contains($"ValueTask<{TypeNameHelper.GetTypeDisplayName(type, fullName: false)}?> BindAsync(HttpContext context, ParameterInfo parameter)", ex.Message); Assert.Contains($"ValueTask<{TypeNameHelper.GetTypeDisplayName(type, fullName: false)}?> BindAsync(HttpContext context)", ex.Message); }
public async Task FindBindAsyncMethod_FindsFallbackMethodFromInheritedWhenPreferredMethodIsInvalid() { var parameterInfo = GetFirstParameter((BindAsyncBadMethod? arg) => BindAsyncBadMethodMethod(arg)); var cache = new ParameterBindingMethodCache(); Assert.True(cache.HasBindAsyncMethod(parameterInfo)); var methodFound = cache.FindBindAsyncMethod(parameterInfo); var parseHttpContext = Expression.Lambda <Func <HttpContext, ValueTask <object> > >(methodFound.Expression !, ParameterBindingMethodCache.HttpContextExpr).Compile(); var httpContext = new DefaultHttpContext(); Assert.Null(await parseHttpContext(httpContext)); }
public void FindTryParseMethod_WithNoFormatProvider(Type type) { var methodFound = new ParameterBindingMethodCache().FindTryParseMethod(@type); Assert.NotNull(methodFound); var call = methodFound !(Expression.Variable(type, "parsedValue"), Expression.Constant(CultureInfo.InvariantCulture)) as MethodCallExpression; Assert.NotNull(call); var parameters = call !.Method.GetParameters(); Assert.Equal(2, parameters.Length); Assert.Equal(typeof(string), parameters[0].ParameterType); Assert.True(parameters[1].IsOut); }
public void FindTryParseStringMethod_ReturnsTheExpectedTryParseMethodWithInvariantCultureCustomType(Type type) { var methodFound = new ParameterBindingMethodCache().FindTryParseMethod(@type); Assert.NotNull(methodFound); var call = methodFound !(Expression.Variable(type, "parsedValue"), Expression.Constant(CultureInfo.InvariantCulture)) as MethodCallExpression; Assert.NotNull(call); var parameters = call !.Method.GetParameters(); Assert.Equal(3, parameters.Length); Assert.Equal(typeof(string), parameters[0].ParameterType); Assert.Equal(typeof(IFormatProvider), parameters[1].ParameterType); Assert.True(parameters[2].IsOut); Assert.True(((call.Arguments[1] as ConstantExpression) !.Value as CultureInfo) !.Equals(CultureInfo.InvariantCulture)); }
public void FindTryParseStringMethod_WorksForEnums() { var type = typeof(Choice); var methodFound = new ParameterBindingMethodCache().FindTryParseMethod(type); Assert.NotNull(methodFound); var call = methodFound !(Expression.Variable(type, "parsedValue"), Expression.Constant(CultureInfo.InvariantCulture)) as MethodCallExpression; Assert.NotNull(call); var method = call !.Method; var parameters = method.GetParameters(); // By default, we use Enum.TryParse<T> Assert.True(method.IsGenericMethod); Assert.Equal(2, parameters.Length); Assert.Equal(typeof(string), parameters[0].ParameterType); Assert.True(parameters[1].IsOut); }
public void FindTryParseStringMethod_WorksForEnumsWhenNonGenericEnumParseIsUsed() { var type = typeof(Choice); var cache = new ParameterBindingMethodCache(preferNonGenericEnumParseOverload: true); var methodFound = cache.FindTryParseMethod(type); Assert.NotNull(methodFound); var parsedValue = Expression.Variable(type, "parsedValue"); var block = methodFound !(parsedValue, Expression.Constant(CultureInfo.InvariantCulture)) as BlockExpression; Assert.NotNull(block); Assert.Equal(typeof(bool), block !.Type); var parseEnum = Expression.Lambda <Func <string, Choice> >(Expression.Block(new[] { parsedValue }, block, parsedValue), ParameterBindingMethodCache.TempSourceStringExpr).Compile(); Assert.Equal(Choice.One, parseEnum("One")); Assert.Equal(Choice.Two, parseEnum("Two")); Assert.Equal(Choice.Three, parseEnum("Three")); }
public void FindTryParseMethod_IgnoresInvalidTryParseIfGoodOneFound(Type type) { var method = new ParameterBindingMethodCache().FindTryParseMethod(type); Assert.NotNull(method); }