Moving IModelValidatorProvider to Options

Fixes #879
This commit is contained in:
Pranav K 2014-08-20 09:33:26 -07:00
parent d77b06f742
commit d604c18368
34 changed files with 606 additions and 129 deletions

View File

@ -526,7 +526,7 @@ namespace Microsoft.AspNet.Mvc
bindingContext.MetadataProvider,
bindingContext.ModelBinder,
valueProvider,
bindingContext.ValidatorProviders);
bindingContext.ValidatorProvider);
}
}
}

View File

@ -266,7 +266,7 @@ namespace Microsoft.AspNet.Mvc
ModelMetadata = modelMetadata,
ModelBinder = actionBindingContext.ModelBinder,
ValueProvider = actionBindingContext.ValueProvider,
ValidatorProviders = actionBindingContext.ValidatorProviders,
ValidatorProvider = actionBindingContext.ValidatorProvider,
MetadataProvider = metadataProvider,
HttpContext = actionBindingContext.ActionContext.HttpContext,
FallbackToEmptyPrefix = true

View File

@ -92,6 +92,12 @@ namespace Microsoft.AspNet.Mvc
/// </summary>
public List<ModelBinderDescriptor> ModelBinders { get; private set; }
/// <summary>
/// Get a list of the <see cref="IModelValidatorProvider" />s used by this application.
/// </summary>
public List<ModelValidatorProviderDescriptor> ModelValidatorProviders { get; } =
new List<ModelValidatorProviderDescriptor>();
/// <summary>
/// Gets a list of descriptors that represent <see cref="Rendering.IViewEngine"/> used
/// by this application.

View File

@ -0,0 +1,37 @@
// 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.Mvc.ModelBinding;
using Microsoft.Framework.DependencyInjection;
using Microsoft.Framework.OptionsModel;
namespace Microsoft.AspNet.Mvc.OptionDescriptors
{
/// <inheritdoc />
public class DefaultModelValidatorProviderProvider : OptionDescriptorBasedProvider<IModelValidatorProvider>,
IModelValidatorProviderProvider
{
/// <summary>
/// Initializes a new instance of the <see cref="DefaultModelValidatorProviderProvider"/> class.
/// </summary>
/// <param name="options">An accessor to the <see cref="MvcOptions"/> configured for this application.</param>
/// <param name="typeActivator">An <see cref="ITypeActivator"/> instance used to instantiate types.</param>
/// <param name="serviceProvider">A <see cref="IServiceProvider"/> instance that retrieves services from the
/// service collection.</param>
public DefaultModelValidatorProviderProvider(
IOptionsAccessor<MvcOptions> optionsAccessor,
ITypeActivator typeActivator,
IServiceProvider serviceProvider)
: base(optionsAccessor.Options.ModelValidatorProviders, typeActivator, serviceProvider)
{
}
/// <inheritdoc />
public IReadOnlyList<IModelValidatorProvider> ModelValidatorProviders
{
get { return Options; }
}
}
}

View File

@ -0,0 +1,32 @@
// 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 Microsoft.AspNet.Mvc.ModelBinding;
namespace Microsoft.AspNet.Mvc.OptionDescriptors
{
/// <summary>
/// Encapsulates information that describes an <see cref="IModelValidatorProvider"/>.
/// </summary>
public class ModelValidatorProviderDescriptor : OptionDescriptor<IModelValidatorProvider>
{
/// <summary>
/// Creates a new instance of <see cref="ModelValidatorProviderDescriptor"/>.
/// </summary>
/// <param name="type">A type that represents a <see cref="IModelValidatorProvider"/>.</param>
public ModelValidatorProviderDescriptor([NotNull] Type type)
: base(type)
{
}
/// <summary>
/// Creates a new instance of <see cref="ModelValidatorProviderDescriptor"/> with the specified instance.
/// </summary>
/// <param name="option">An instance of <see cref="IModelValidatorProvider"/>.</param>
public ModelValidatorProviderDescriptor([NotNull] IModelValidatorProvider validatorProvider)
: base(validatorProvider)
{
}
}
}

View File

@ -0,0 +1,94 @@
// 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.Mvc.ModelBinding;
using Microsoft.AspNet.Mvc.OptionDescriptors;
namespace Microsoft.AspNet.Mvc
{
/// <summary>
/// Extension methods for adding validator provider to a collection.
/// </summary>
public static class ModelValidatorProviderDescriptorExtensions
{
/// <summary>
/// Adds a type representing a <see cref="IModelValidatorProvider"/> to <paramref name="descriptors"/>.
/// </summary>
/// <param name="descriptors">A list of <see cref="ModelValidatorProviderDescriptor"/>.</param>
/// <param name="modelValidatorProviderType">Type representing an <see cref="IModelValidatorProvider"/></param>
/// <returns>A <see cref="ModelValidatorProviderDescriptor"/> representing the added instance.</returns>
public static ModelValidatorProviderDescriptor Add(
[NotNull] this IList<ModelValidatorProviderDescriptor> descriptors,
[NotNull] Type modelValidatorProviderType)
{
var descriptor = new ModelValidatorProviderDescriptor(modelValidatorProviderType);
descriptors.Add(descriptor);
return descriptor;
}
/// <summary>
/// Inserts a type representing a <see cref="IModelValidatorProvider"/> in to <paramref name="descriptors"/> at
/// the specified <paramref name="index"/>.
/// </summary>
/// <param name="descriptors">A list of <see cref="ModelValidatorProviderDescriptor"/>.</param>
/// <param name="index">The zero-based index at which <paramref name="modelValidatorProviderType"/>
/// should be inserted.</param>
/// <param name="modelValidatorProviderType">Type representing an <see cref="IModelValidatorProvider"/></param>
/// <returns>A <see cref="ModelValidatorProviderDescriptor"/> representing the inserted instance.</returns>
public static ModelValidatorProviderDescriptor Insert(
[NotNull] this IList<ModelValidatorProviderDescriptor> descriptors,
int index,
[NotNull] Type modelValidatorProviderType)
{
if (index < 0 || index > descriptors.Count)
{
throw new ArgumentOutOfRangeException(nameof(index));
}
var descriptor = new ModelValidatorProviderDescriptor(modelValidatorProviderType);
descriptors.Insert(index, descriptor);
return descriptor;
}
/// <summary>
/// Adds an <see cref="IModelValidatorProvider"/> to <paramref name="descriptors"/>.
/// </summary>
/// <param name="descriptors">A list of <see cref="ModelValidatorProviderDescriptor"/>.</param>
/// <param name="modelValidatorProvider">An <see cref="IModelBinder"/> instance.</param>
/// <returns>A <see cref="ModelValidatorProviderDescriptor"/> representing the added instance.</returns>
public static ModelValidatorProviderDescriptor Add(
[NotNull] this IList<ModelValidatorProviderDescriptor> descriptors,
[NotNull] IModelValidatorProvider modelValidatorProvider)
{
var descriptor = new ModelValidatorProviderDescriptor(modelValidatorProvider);
descriptors.Add(descriptor);
return descriptor;
}
/// <summary>
/// Insert an <see cref="IModelValidatorProvider"/> in to <paramref name="descriptors"/> at the specified
/// <paramref name="index"/>.
/// </summary>
/// <param name="descriptors">A list of <see cref="ModelValidatorProviderDescriptor"/>.</param>
/// <param name="index">The zero-based index at which <paramref name="modelValidatorProvider"/>
/// should be inserted.</param>
/// <param name="modelValidatorProvider">An <see cref="IModelBinder"/> instance.</param>
/// <returns>A <see cref="ModelValidatorProviderDescriptor"/> representing the added instance.</returns>
public static ModelValidatorProviderDescriptor Insert(
[NotNull] this IList<ModelValidatorProviderDescriptor> descriptors,
int index,
[NotNull] IModelValidatorProvider modelValidatorProvider)
{
if (index < 0 || index > descriptors.Count)
{
throw new ArgumentOutOfRangeException(nameof(index));
}
var descriptor = new ModelValidatorProviderDescriptor(modelValidatorProvider);
descriptors.Insert(index, descriptor);
return descriptor;
}
}
}

View File

@ -1,7 +1,6 @@
// 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.Collections.Generic;
using Microsoft.AspNet.Mvc.ModelBinding;
namespace Microsoft.AspNet.Mvc
@ -13,14 +12,14 @@ namespace Microsoft.AspNet.Mvc
IModelBinder modelBinder,
IValueProvider valueProvider,
IInputFormatterSelector inputFormatterSelector,
IEnumerable<IModelValidatorProvider> validatorProviders)
IModelValidatorProvider validatorProvider)
{
ActionContext = context;
MetadataProvider = metadataProvider;
ModelBinder = modelBinder;
ValueProvider = valueProvider;
InputFormatterSelector = inputFormatterSelector;
ValidatorProviders = validatorProviders;
ValidatorProvider = validatorProvider;
}
public ActionContext ActionContext { get; private set; }
@ -33,6 +32,6 @@ namespace Microsoft.AspNet.Mvc
public IInputFormatterSelector InputFormatterSelector { get; private set; }
public IEnumerable<IModelValidatorProvider> ValidatorProviders { get; private set; }
public IModelValidatorProvider ValidatorProvider { get; private set; }
}
}

View File

@ -2,7 +2,6 @@
// 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.Threading.Tasks;
using Microsoft.AspNet.Mvc.ModelBinding;
@ -14,20 +13,20 @@ namespace Microsoft.AspNet.Mvc
private readonly ICompositeModelBinder _compositeModelBinder;
private readonly IValueProviderFactory _compositeValueProviderFactory;
private readonly IInputFormatterSelector _inputFormatterSelector;
private readonly IEnumerable<IModelValidatorProvider> _validatorProviders;
private readonly ICompositeModelValidatorProvider _validatorProvider;
private Tuple<ActionContext, ActionBindingContext> _bindingContext;
public DefaultActionBindingContextProvider(IModelMetadataProvider modelMetadataProvider,
ICompositeModelBinder compositeModelBinder,
ICompositeValueProviderFactory compositeValueProviderFactory,
IInputFormatterSelector inputFormatterProvider,
IEnumerable<IModelValidatorProvider> validatorProviders)
ICompositeModelValidatorProvider validatorProvider)
{
_modelMetadataProvider = modelMetadataProvider;
_compositeModelBinder = compositeModelBinder;
_compositeValueProviderFactory = compositeValueProviderFactory;
_inputFormatterSelector = inputFormatterProvider;
_validatorProviders = validatorProviders;
_validatorProvider = validatorProvider;
}
public Task<ActionBindingContext> GetActionBindingContextAsync(ActionContext actionContext)
@ -52,7 +51,7 @@ namespace Microsoft.AspNet.Mvc
_compositeModelBinder,
valueProvider,
_inputFormatterSelector,
_validatorProviders);
_validatorProvider);
_bindingContext = new Tuple<ActionContext, ActionBindingContext>(actionContext, context);

View File

@ -23,8 +23,8 @@ namespace Microsoft.AspNet.Mvc
/// <param name="metadataProvider">The provider used for reading metadata for the model type.</param>
/// <param name="modelBinder">The model binder used for binding.</param>
/// <param name="valueProvider">The value provider used for looking up values.</param>
/// <param name="validatorProviders">The validator providers used for executing validation
/// on the model instance.</param>
/// <param name="validatorProvider">The validator provider used for executing validation on the model
/// instance.</param>
/// <returns>A Task with a value representing if the the update is successful.</returns>
public static async Task<bool> TryUpdateModelAsync<TModel>(
[NotNull] TModel model,
@ -34,7 +34,7 @@ namespace Microsoft.AspNet.Mvc
[NotNull] IModelMetadataProvider metadataProvider,
[NotNull] IModelBinder modelBinder,
[NotNull] IValueProvider valueProvider,
[NotNull] IEnumerable<IModelValidatorProvider> validatorProviders)
[NotNull] IModelValidatorProvider validatorProvider)
where TModel : class
{
var modelMetadata = metadataProvider.GetMetadataForType(
@ -49,7 +49,7 @@ namespace Microsoft.AspNet.Mvc
ModelState = modelState,
ModelBinder = modelBinder,
ValueProvider = valueProvider,
ValidatorProviders = validatorProviders,
ValidatorProvider = validatorProvider,
MetadataProvider = metadataProvider,
FallbackToEmptyPrefix = true,
HttpContext = httpContext

View File

@ -1315,13 +1315,12 @@ namespace Microsoft.AspNet.Mvc.Rendering
string name)
{
var actionBindingContext = _actionBindingContextProvider.GetActionBindingContextAsync(ViewContext).Result;
metadata = metadata ??
ExpressionMetadataProvider.FromStringExpression(name, ViewData, MetadataProvider);
return actionBindingContext.ValidatorProviders
.SelectMany(vp => vp.GetValidators(metadata))
.OfType<IClientModelValidator>()
.SelectMany(v => v.GetClientValidationRules(
new ClientModelValidationContext(metadata, MetadataProvider)));
metadata = metadata ?? ExpressionMetadataProvider.FromStringExpression(name, ViewData, MetadataProvider);
return actionBindingContext.ValidatorProvider
.GetValidators(metadata)
.OfType<IClientModelValidator>()
.SelectMany(v => v.GetClientValidationRules(
new ClientModelValidationContext(metadata, MetadataProvider)));
}
// Only need a dictionary if htmlAttributes is non-null. TagBuilder.MergeAttributes() is fine with null.

View File

@ -80,7 +80,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
}
var validationContext = new ModelValidationContext(bindingContext.MetadataProvider,
bindingContext.ValidatorProviders,
bindingContext.ValidatorProvider,
bindingContext.ModelState,
bindingContext.ModelMetadata,
containerMetadata: null);
@ -120,7 +120,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
ModelName = modelName,
ModelState = oldBindingContext.ModelState,
ValueProvider = oldBindingContext.ValueProvider,
ValidatorProviders = oldBindingContext.ValidatorProviders,
ValidatorProvider = oldBindingContext.ValidatorProvider,
MetadataProvider = oldBindingContext.MetadataProvider,
ModelBinder = oldBindingContext.ModelBinder,
HttpContext = oldBindingContext.HttpContext

View File

@ -170,8 +170,9 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
{
var propertyName = property.Name;
var propertyMetadata = bindingContext.PropertyMetadata[propertyName];
var requiredValidator = bindingContext.GetValidators(propertyMetadata)
.FirstOrDefault(v => v.IsRequired);
var requiredValidator = bindingContext.ValidatorProvider
.GetValidators(propertyMetadata)
.FirstOrDefault(v => v != null && v.IsRequired);
if (requiredValidator != null)
{
validationInfo.RequiredValidators[propertyName] = requiredValidator;

View File

@ -1,26 +0,0 @@
// 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.Collections.Generic;
using System.Linq;
namespace Microsoft.AspNet.Mvc.ModelBinding.Internal
{
internal static class ModelBindingContextExtensions
{
public static IEnumerable<IModelValidator> GetValidators([NotNull] this ModelBindingContext context,
[NotNull] ModelMetadata metadata)
{
return context.ValidatorProviders.SelectMany(vp => vp.GetValidators(metadata))
.Where(v => v != null);
}
public static IEnumerable<ModelValidationResult> Validate([NotNull] this ModelBindingContext bindingContext)
{
var validators = GetValidators(bindingContext, bindingContext.ModelMetadata);
var compositeValidator = new CompositeModelValidator(validators);
var modelValidationContext = new ModelValidationContext(bindingContext, bindingContext.ModelMetadata);
return compositeValidator.Validate(modelValidationContext);
}
}
}

View File

@ -41,7 +41,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
ValueProvider = bindingContext.ValueProvider;
MetadataProvider = bindingContext.MetadataProvider;
ModelBinder = bindingContext.ModelBinder;
ValidatorProviders = bindingContext.ValidatorProviders;
ValidatorProvider = bindingContext.ValidatorProvider;
HttpContext = bindingContext.HttpContext;
}
}
@ -148,10 +148,10 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
public IModelMetadataProvider MetadataProvider { get; set; }
/// <summary>
/// Gets or sets the sequence of <see cref="IModelValidatorProvider"/> instances used for model validation
/// with this context.
/// Gets or sets the <see cref="IModelValidatorProvider"/> instance used for model validation with this
/// context.
/// </summary>
public IEnumerable<IModelValidatorProvider> ValidatorProviders { get; set; }
public IModelValidatorProvider ValidatorProvider { get; set; }
/// <summary>
/// Gets a dictionary of property name to <see cref="ModelMetadata"/> instances for

View File

@ -0,0 +1,31 @@
// 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.Collections.Generic;
using System.Linq;
namespace Microsoft.AspNet.Mvc.ModelBinding
{
/// <summary>
/// Default implementation for <see cref="ICompositeModelValidatorProvider"/>.
/// </summary>
public class CompositeModelValidatorProvider : ICompositeModelValidatorProvider
{
/// <summary>
/// Initializes a new instance of <see cref="CompositeModelValidatorProvider"/>.
/// </summary>
/// <param name="provider">The <see cref="IModelValidatorProviderProvider"/> instance used to get the list of
/// activated <see cref="IModelValidatorProvider"/> that this instance delegates to.</param>
public CompositeModelValidatorProvider(IModelValidatorProviderProvider provider)
{
ValidatorProviders = provider.ModelValidatorProviders;
}
public IReadOnlyList<IModelValidatorProvider> ValidatorProviders { get; private set; }
public IEnumerable<IModelValidator> GetValidators(ModelMetadata metadata)
{
return ValidatorProviders.SelectMany(v => v.GetValidators(metadata));
}
}
}

View File

@ -0,0 +1,12 @@
// 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.
namespace Microsoft.AspNet.Mvc.ModelBinding
{
/// <summary>
/// Represents aggregate of <see cref="IModelValidatorProvider"/>s that delegates to its underlying providers.
/// </summary>
public interface ICompositeModelValidatorProvider : IModelValidatorProvider
{
}
}

View File

@ -0,0 +1,18 @@
// 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.Collections.Generic;
namespace Microsoft.AspNet.Mvc.ModelBinding
{
/// <summary>
/// Provides an activated collection of <see cref="IModelValidatorProvider"/> instances.
/// </summary>
public interface IModelValidatorProviderProvider
{
/// <summary>
/// Gets a collection of activated <see cref="IModelValidatorProvider"/> instances.
/// </summary>
IReadOnlyList<IModelValidatorProvider> ModelValidatorProviders { get; }
}
}

View File

@ -1,32 +1,30 @@
// 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.Collections.Generic;
namespace Microsoft.AspNet.Mvc.ModelBinding
{
public class ModelValidationContext
{
public ModelValidationContext([NotNull] ModelBindingContext bindingContext,
[NotNull] ModelMetadata metadata)
: this(bindingContext.MetadataProvider,
bindingContext.ValidatorProviders,
bindingContext.ModelState,
metadata,
: this(bindingContext.MetadataProvider,
bindingContext.ValidatorProvider,
bindingContext.ModelState,
metadata,
bindingContext.ModelMetadata)
{
}
public ModelValidationContext([NotNull] IModelMetadataProvider metadataProvider,
[NotNull] IEnumerable<IModelValidatorProvider> validatorProviders,
[NotNull] ModelStateDictionary modelState,
[NotNull] ModelMetadata metadata,
public ModelValidationContext([NotNull] IModelMetadataProvider metadataProvider,
[NotNull] IModelValidatorProvider validatorProvider,
[NotNull] ModelStateDictionary modelState,
[NotNull] ModelMetadata metadata,
ModelMetadata containerMetadata)
{
ModelMetadata = metadata;
ModelState = modelState;
MetadataProvider = metadataProvider;
ValidatorProviders = validatorProviders;
ValidatorProvider = validatorProvider;
ContainerMetadata = containerMetadata;
}
@ -37,7 +35,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
ContainerMetadata = parentContext.ModelMetadata;
ModelState = parentContext.ModelState;
MetadataProvider = parentContext.MetadataProvider;
ValidatorProviders = parentContext.ValidatorProviders;
ValidatorProvider = parentContext.ValidatorProvider;
}
public ModelMetadata ModelMetadata { get; private set; }
@ -48,6 +46,6 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
public IModelMetadataProvider MetadataProvider { get; private set; }
public IEnumerable<IModelValidatorProvider> ValidatorProviders { get; private set; }
public IModelValidatorProvider ValidatorProvider { get; private set; }
}
}

View File

@ -215,7 +215,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
private static IEnumerable<IModelValidator> GetValidators(ModelValidationContext validationContext,
ModelMetadata metadata)
{
return validationContext.ValidatorProviders.SelectMany(vp => vp.GetValidators(metadata));
return validationContext.ValidatorProvider.GetValidators(metadata);
}
}
}

View File

@ -1,9 +1,7 @@
// 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.Collections.Generic;
using Microsoft.AspNet.Mvc.ModelBinding;
using Microsoft.AspNet.Mvc.OptionDescriptors;
using Microsoft.AspNet.Mvc.Razor;
using Microsoft.Framework.OptionsModel;
@ -54,6 +52,10 @@ namespace Microsoft.AspNet.Mvc
options.ValueProviderFactories.Add(new RouteValueValueProviderFactory());
options.ValueProviderFactories.Add(new QueryStringValueProviderFactory());
options.ValueProviderFactories.Add(new FormValueProviderFactory());
// Set up validators
options.ModelValidatorProviders.Add(new DataAnnotationsModelValidatorProvider());
options.ModelValidatorProviders.Add(new DataMemberModelValidatorProvider());
}
}
}

View File

@ -81,8 +81,8 @@ namespace Microsoft.AspNet.Mvc
yield return describe.Transient<INestedProvider<FilterProviderContext>, DefaultFilterProvider>();
yield return describe.Transient<IModelValidatorProvider, DataAnnotationsModelValidatorProvider>();
yield return describe.Transient<IModelValidatorProvider, DataMemberModelValidatorProvider>();
yield return describe.Transient<IModelValidatorProviderProvider, DefaultModelValidatorProviderProvider>();
yield return describe.Scoped<ICompositeModelValidatorProvider, CompositeModelValidatorProvider>();
yield return describe.Scoped<IUrlHelper, UrlHelper>();

View File

@ -578,7 +578,7 @@ namespace Microsoft.AspNet.Mvc.Test
binder.Object,
valueProvider,
Mock.Of<IInputFormatterSelector>(),
Enumerable.Empty<IModelValidatorProvider>());
Mock.Of<IModelValidatorProvider>());
var bindingContextProvider = new Mock<IActionBindingContextProvider>();
bindingContextProvider.Setup(b => b.GetActionBindingContextAsync(actionContext))
.Returns(Task.FromResult(bindingContext));
@ -619,7 +619,7 @@ namespace Microsoft.AspNet.Mvc.Test
binder.Object,
valueProvider,
Mock.Of<IInputFormatterSelector>(),
Enumerable.Empty<IModelValidatorProvider>());
Mock.Of<IModelValidatorProvider>());
var bindingContextProvider = new Mock<IActionBindingContextProvider>();
bindingContextProvider.Setup(b => b.GetActionBindingContextAsync(actionContext))
.Returns(Task.FromResult(bindingContext));
@ -660,7 +660,7 @@ namespace Microsoft.AspNet.Mvc.Test
binder.Object,
Mock.Of<IValueProvider>(),
Mock.Of<IInputFormatterSelector>(),
Enumerable.Empty<IModelValidatorProvider>());
Mock.Of<IModelValidatorProvider>());
var bindingContextProvider = new Mock<IActionBindingContextProvider>();
bindingContextProvider.Setup(b => b.GetActionBindingContextAsync(actionContext))
.Returns(Task.FromResult(bindingContext));

View File

@ -0,0 +1,66 @@
// 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.Mvc.ModelBinding;
using Microsoft.Framework.DependencyInjection;
using Microsoft.Framework.OptionsModel;
using Moq;
using Xunit;
namespace Microsoft.AspNet.Mvc.OptionDescriptors
{
public class DefaultValidationProviderProviderTest
{
[Fact]
public void ValidationProviders_ReturnsInstantiatedListOfValueProviders()
{
// Arrange
var service = Mock.Of<ITestService>();
var validationProvider = Mock.Of<IModelValidatorProvider>();
var type = typeof(TestModelValidationProvider);
var typeActivator = new TypeActivator();
var serviceProvider = new Mock<IServiceProvider>();
serviceProvider.Setup(p => p.GetService(typeof(ITestService)))
.Returns(service);
var options = new MvcOptions();
options.ModelValidatorProviders.Add(type);
options.ModelValidatorProviders.Add(validationProvider);
var accessor = new Mock<IOptionsAccessor<MvcOptions>>();
accessor.SetupGet(a => a.Options)
.Returns(options);
var provider = new DefaultModelValidatorProviderProvider(accessor.Object,
typeActivator,
serviceProvider.Object);
// Act
var result = provider.ModelValidatorProviders;
// Assert
Assert.Equal(2, result.Count);
var testModelValidationProvider = Assert.IsType<TestModelValidationProvider>(result[0]);
Assert.Same(service, testModelValidationProvider.Service);
Assert.Same(validationProvider, result[1]);
}
private class TestModelValidationProvider : IModelValidatorProvider
{
public TestModelValidationProvider(ITestService service)
{
Service = service;
}
public ITestService Service { get; private set; }
public IEnumerable<IModelValidator> GetValidators(ModelMetadata metadata)
{
throw new NotImplementedException();
}
}
public interface ITestService
{
}
}
}

View File

@ -0,0 +1,63 @@
// 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.Mvc.ModelBinding;
using Microsoft.AspNet.Testing;
using Xunit;
namespace Microsoft.AspNet.Mvc.OptionDescriptors
{
public class ModelValidatorProviderDescriptorTest
{
[Fact]
public void ConstructorThrows_IfTypeIsNotModelValidatorProvider()
{
// Arrange
var validatorProviderType = typeof(IModelValidatorProvider).FullName;
var type = typeof(string);
var expected = string.Format("The type '{0}' must derive from '{1}'.",
type.FullName, validatorProviderType);
// Act & Assert
ExceptionAssert.ThrowsArgument(() => new ModelValidatorProviderDescriptor(type), "type", expected);
}
[Fact]
public void ConstructorSetsModelValidatorProviderType()
{
// Arrange
var type = typeof(TestModelValidatorProvider);
// Act
var descriptor = new ModelValidatorProviderDescriptor(type);
// Assert
Assert.Equal(type, descriptor.OptionType);
Assert.Null(descriptor.Instance);
}
[Fact]
public void ConstructorSetsInstanceAndType()
{
// Arrange
var validatorProvider = new TestModelValidatorProvider();
// Act
var descriptor = new ModelValidatorProviderDescriptor(validatorProvider);
// Assert
Assert.Same(validatorProvider, descriptor.Instance);
Assert.Equal(validatorProvider.GetType(), descriptor.OptionType);
}
private class TestModelValidatorProvider : IModelValidatorProvider
{
public IEnumerable<IModelValidator> GetValidators(ModelMetadata metadata)
{
throw new NotImplementedException();
}
}
}
}

View File

@ -0,0 +1,73 @@
// 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.Mvc.ModelBinding;
using Microsoft.AspNet.Mvc.OptionDescriptors;
using Moq;
using Xunit;
namespace Microsoft.AspNet.Mvc
{
public class ModelValidatorProviderDescriptorExtensionsTest
{
[Theory]
[InlineData(-1)]
[InlineData(5)]
public void Insert_WithType_ThrowsIfIndexIsOutOfBounds(int index)
{
// Arrange
var collection = new List<ModelValidatorProviderDescriptor>
{
new ModelValidatorProviderDescriptor(Mock.Of<IModelValidatorProvider>()),
new ModelValidatorProviderDescriptor(Mock.Of<IModelValidatorProvider>())
};
// Act & Assert
Assert.Throws<ArgumentOutOfRangeException>("index",
() => collection.Insert(index, typeof(IModelValidatorProvider)));
}
[Theory]
[InlineData(-2)]
[InlineData(3)]
public void Insert_WithInstance_ThrowsIfIndexIsOutOfBounds(int index)
{
// Arrange
var collection = new List<ModelValidatorProviderDescriptor>
{
new ModelValidatorProviderDescriptor(Mock.Of<IModelValidatorProvider>()),
new ModelValidatorProviderDescriptor(Mock.Of<IModelValidatorProvider>())
};
var valueProviderFactory = Mock.Of<IModelValidatorProvider>();
// Act & Assert
Assert.Throws<ArgumentOutOfRangeException>("index", () => collection.Insert(index, valueProviderFactory));
}
[InlineData]
public void ModelValidatorProviderDescriptors_AddsTypesAndInstances()
{
// Arrange
var provider1 = Mock.Of<IModelValidatorProvider>();
var provider2 = Mock.Of<IModelValidatorProvider>();
var type1 = typeof(DataMemberModelValidatorProvider);
var type2 = typeof(DataAnnotationsModelValidatorProvider);
var collection = new List<ModelValidatorProviderDescriptor>();
// Act
collection.Add(provider2);
collection.Insert(0, provider1);
collection.Add(type2);
collection.Insert(2, type1);
// Assert
Assert.Equal(4, collection.Count);
Assert.Same(provider1, collection[0].Instance);
Assert.Same(provider2, collection[1].Instance);
Assert.IsType<DataMemberModelValidatorProvider>(collection[2].OptionType);
Assert.IsType<DataAnnotationsModelValidatorProvider>(collection[3].OptionType);
}
}
}

View File

@ -5,7 +5,6 @@
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNet.Http;
using Microsoft.AspNet.Mvc.ModelBinding;
@ -39,7 +38,7 @@ namespace Microsoft.AspNet.Mvc.Core.Test
metadataProvider.Object,
GetCompositeBinder(binder.Object),
Mock.Of<IValueProvider>(),
Enumerable.Empty<IModelValidatorProvider>());
Mock.Of<IModelValidatorProvider>());
// Assert
Assert.False(result);
@ -76,7 +75,7 @@ namespace Microsoft.AspNet.Mvc.Core.Test
new DataAnnotationsModelMetadataProvider(),
GetCompositeBinder(binders),
valueProvider,
new[] { validator });
validator);
// Assert
Assert.False(result);
@ -114,7 +113,7 @@ namespace Microsoft.AspNet.Mvc.Core.Test
new DataAnnotationsModelMetadataProvider(),
GetCompositeBinder(binders),
valueProvider,
new[] { validator });
validator);
// Assert
Assert.True(result);

View File

@ -1371,7 +1371,7 @@ namespace Microsoft.AspNet.Mvc
binder.Object,
Mock.Of<IValueProvider>(),
Mock.Of<IInputFormatterSelector>(),
Enumerable.Empty<IModelValidatorProvider>());
Mock.Of<IModelValidatorProvider>());
var actionBindingContextProvider = new Mock<IActionBindingContextProvider>();
actionBindingContextProvider.Setup(p => p.GetActionBindingContextAsync(It.IsAny<ActionContext>()))
@ -1430,7 +1430,7 @@ namespace Microsoft.AspNet.Mvc
binder.Object,
Mock.Of<IValueProvider>(),
Mock.Of<IInputFormatterSelector>(),
Enumerable.Empty<IModelValidatorProvider>());
Mock.Of<IModelValidatorProvider>());
var actionBindingContextProvider = new Mock<IActionBindingContextProvider>();
actionBindingContextProvider.Setup(p => p.GetActionBindingContextAsync(It.IsAny<ActionContext>()))
@ -1481,7 +1481,7 @@ namespace Microsoft.AspNet.Mvc
Mock.Of<IModelBinder>(),
Mock.Of<IValueProvider>(),
Mock.Of<IInputFormatterSelector>(),
Enumerable.Empty<IModelValidatorProvider>());
Mock.Of<IModelValidatorProvider>());
var actionBindingContextProvider = new Mock<IActionBindingContextProvider>();
actionBindingContextProvider.Setup(p => p.GetActionBindingContextAsync(It.IsAny<ActionContext>()))
@ -1548,7 +1548,7 @@ namespace Microsoft.AspNet.Mvc
binder.Object,
Mock.Of<IValueProvider>(),
Mock.Of<IInputFormatterSelector>(),
Enumerable.Empty<IModelValidatorProvider>());
Mock.Of<IModelValidatorProvider>());
var actionBindingContextProvider = new Mock<IActionBindingContextProvider>();
actionBindingContextProvider.Setup(p => p.GetActionBindingContextAsync(It.IsAny<ActionContext>()))

View File

@ -93,7 +93,7 @@ namespace Microsoft.AspNet.Mvc.Core
Mock.Of<IModelBinder>(),
Mock.Of<IValueProvider>(),
Mock.Of<IInputFormatterSelector>(),
Enumerable.Empty<IModelValidatorProvider>());
Mock.Of<IModelValidatorProvider>());
var urlHelper = Mock.Of<IUrlHelper>();
var actionBindingContextProvider = new Mock<IActionBindingContextProvider>();
actionBindingContextProvider

View File

@ -31,7 +31,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding.Test
{
{ "someName", "dummyValue" }
},
ValidatorProviders = Enumerable.Empty<IModelValidatorProvider>()
ValidatorProvider = GetValidatorProvider()
};
var mockIntBinder = new Mock<IModelBinder>();
@ -78,14 +78,14 @@ namespace Microsoft.AspNet.Mvc.ModelBinding.Test
{
{ "someOtherName", "dummyValue" }
},
ValidatorProviders = Enumerable.Empty<IModelValidatorProvider>()
ValidatorProvider = GetValidatorProvider()
};
var mockIntBinder = new Mock<IModelBinder>();
mockIntBinder
.Setup(o => o.BindModelAsync(It.IsAny<ModelBindingContext>()))
.Returns(
delegate(ModelBindingContext mbc)
delegate (ModelBindingContext mbc)
{
if (!string.IsNullOrEmpty(mbc.ModelName))
{
@ -122,7 +122,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding.Test
.Returns(Task.FromResult(false))
.Verifiable();
var shimBinder = (IModelBinder)mockListBinder.Object;
var shimBinder = mockListBinder.Object;
var bindingContext = new ModelBindingContext
{
@ -233,7 +233,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding.Test
{ "user.password", "password-val" },
{ "user.confirmpassword", "not-password-val" },
};
var bindingContext = CreateBindingContext(binder, valueProvider, typeof(User), new[] { validatorProvider });
var bindingContext = CreateBindingContext(binder, valueProvider, typeof(User), validatorProvider);
bindingContext.ModelName = "user";
// Act
@ -255,7 +255,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding.Test
{ "user.password", "password" },
{ "user.confirmpassword", "password" },
};
var bindingContext = CreateBindingContext(binder, valueProvider, typeof(User), new[] { validatorProvider });
var bindingContext = CreateBindingContext(binder, valueProvider, typeof(User), validatorProvider);
bindingContext.ModelName = "user";
// Act
@ -269,9 +269,9 @@ namespace Microsoft.AspNet.Mvc.ModelBinding.Test
private static ModelBindingContext CreateBindingContext(IModelBinder binder,
IValueProvider valueProvider,
Type type,
IEnumerable<IModelValidatorProvider> validatorProviders = null)
IModelValidatorProvider validatorProvider = null)
{
validatorProviders = validatorProviders ?? Enumerable.Empty<IModelValidatorProvider>();
validatorProvider = validatorProvider ?? GetValidatorProvider();
var metadataProvider = new DataAnnotationsModelMetadataProvider();
var bindingContext = new ModelBindingContext
{
@ -281,7 +281,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding.Test
ModelMetadata = metadataProvider.GetMetadataForType(null, type),
ModelState = new ModelStateDictionary(),
ValueProvider = valueProvider,
ValidatorProviders = validatorProviders
ValidatorProvider = validatorProvider
};
return bindingContext;
}
@ -293,8 +293,8 @@ namespace Microsoft.AspNet.Mvc.ModelBinding.Test
typeActivator
.Setup(t => t.CreateInstance(serviceProvider, It.IsAny<Type>(), It.IsAny<object[]>()))
.Returns((IServiceProvider sp, Type t, object[] args) => Activator.CreateInstance(t));
var binders = new IModelBinder[]
{
var binders = new IModelBinder[]
{
new TypeMatchModelBinder(),
new ByteArrayModelBinder(),
new GenericModelBinder(serviceProvider, typeActivator.Object),
@ -319,6 +319,15 @@ namespace Microsoft.AspNet.Mvc.ModelBinding.Test
return shimBinder;
}
private static IModelValidatorProvider GetValidatorProvider(params IModelValidator[] validators)
{
var provider = new Mock<IModelValidatorProvider>();
provider.Setup(v => v.GetValidators(It.IsAny<ModelMetadata>()))
.Returns(validators ?? Enumerable.Empty<IModelValidator>());
return provider.Object;
}
private class SimplePropertiesModel
{
public string FirstName { get; set; }

View File

@ -122,7 +122,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding.Test
ValueProvider = valueProvider,
ModelBinder = innerBinder ?? CreateIntBinder(),
MetadataProvider = metataProvider,
ValidatorProviders = Enumerable.Empty<IModelValidatorProvider>()
ValidatorProvider = Mock.Of<IModelValidatorProvider>()
};
return bindingContext;
}

View File

@ -32,7 +32,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
ValueProvider = mockValueProvider.Object,
ModelBinder = mockDtoBinder.Object,
MetadataProvider = new DataAnnotationsModelMetadataProvider(),
ValidatorProviders = Enumerable.Empty<IModelValidatorProvider>()
ValidatorProvider = Mock.Of<IModelValidatorProvider>()
};
mockDtoBinder
@ -194,7 +194,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
var bindingContext = new ModelBindingContext
{
ModelMetadata = GetMetadataForType(typeof(PersonWithBindExclusion)),
ValidatorProviders = Enumerable.Empty<IModelValidatorProvider>()
ValidatorProvider = Mock.Of<IModelValidatorProvider>()
};
var testableBinder = new TestableMutableObjectModelBinder();
@ -215,7 +215,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
var bindingContext = new ModelBindingContext
{
ModelMetadata = GetMetadataForType(typeof(Person)),
ValidatorProviders = Enumerable.Empty<IModelValidatorProvider>()
ValidatorProvider = Mock.Of<IModelValidatorProvider>()
};
var testableBinder = new TestableMutableObjectModelBinder();
@ -235,7 +235,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
var bindingContext = new ModelBindingContext
{
ModelMetadata = GetMetadataForObject(new ModelWithMixedBindingBehaviors()),
ValidatorProviders = Enumerable.Empty<IModelValidatorProvider>()
ValidatorProvider = Mock.Of<IModelValidatorProvider>()
};
// Act
@ -256,7 +256,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
var modelMetadata = GetMetadataForType(typeof(Person));
var validationNode = new ModelValidationNode(modelMetadata, "foo");
var validationContext = new ModelValidationContext(new DataAnnotationsModelMetadataProvider(),
Enumerable.Empty<IModelValidatorProvider>(),
Mock.Of<IModelValidatorProvider>(),
modelState,
modelMetadata,
null);
@ -278,7 +278,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
var modelMetadata = GetMetadataForType(typeof(Person));
var validationNode = new ModelValidationNode(modelMetadata, "foo");
var validationContext = new ModelValidationContext(new DataAnnotationsModelMetadataProvider(),
Enumerable.Empty<IModelValidatorProvider>(),
Mock.Of<IModelValidatorProvider>(),
modelState,
modelMetadata,
null);
@ -309,7 +309,7 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
{
ModelMetadata = containerMetadata,
ModelName = "theModel",
ValidatorProviders = Enumerable.Empty<IModelValidatorProvider>()
ValidatorProvider = Mock.Of<IModelValidatorProvider>()
};
var dto = new ComplexModelDto(containerMetadata, containerMetadata.Properties);
@ -354,10 +354,10 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
ModelMetadata = containerMetadata,
ModelName = "theModel",
ModelState = new ModelStateDictionary(),
ValidatorProviders = Enumerable.Empty<IModelValidatorProvider>()
ValidatorProvider = Mock.Of<IModelValidatorProvider>()
};
var validationContext = new ModelValidationContext(new EmptyModelMetadataProvider(),
bindingContext.ValidatorProviders,
bindingContext.ValidatorProvider,
bindingContext.ModelState,
containerMetadata,
null);
@ -590,10 +590,9 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
var propertyMetadata = bindingContext.ModelMetadata.Properties.First(o => o.PropertyName == "PropertyWithDefaultValue");
var validationNode = new ModelValidationNode(propertyMetadata, "foo");
var dtoResult = new ComplexModelDtoResult(model: null, validationNode: validationNode);
var requiredValidator = bindingContext.ValidatorProviders
.SelectMany(v => v.GetValidators(propertyMetadata))
.Where(v => v.IsRequired)
.FirstOrDefault();
var requiredValidator = bindingContext.ValidatorProvider
.GetValidators(propertyMetadata)
.FirstOrDefault(v => v.IsRequired);
var testableBinder = new TestableMutableObjectModelBinder();
@ -634,10 +633,9 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
var propertyMetadata = bindingContext.ModelMetadata.Properties.Single(o => o.PropertyName == "DateOfBirth");
var validationNode = new ModelValidationNode(propertyMetadata, "foo");
var dtoResult = new ComplexModelDtoResult(new DateTime(2001, 1, 1), validationNode);
var requiredValidator = bindingContext.ValidatorProviders
.SelectMany(v => v.GetValidators(propertyMetadata))
.Where(v => v.IsRequired)
.FirstOrDefault();
var requiredValidator = bindingContext.ValidatorProvider
.GetValidators(propertyMetadata)
.FirstOrDefault(v => v.IsRequired);
var validationContext = new ModelValidationContext(bindingContext, propertyMetadata);
var testableBinder = new TestableMutableObjectModelBinder();
@ -769,42 +767,45 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
private static ModelBindingContext CreateContext(ModelMetadata metadata)
{
var provider = new Mock<IModelValidatorProviderProvider>();
provider.SetupGet(p => p.ModelValidatorProviders)
.Returns(new IModelValidatorProvider[]
{
new DataAnnotationsModelValidatorProvider(),
new DataMemberModelValidatorProvider()
});
return new ModelBindingContext
{
ModelState = new ModelStateDictionary(),
ModelMetadata = metadata,
ModelName = "theModel",
ValidatorProviders = new IModelValidatorProvider[]
{
new DataAnnotationsModelValidatorProvider(),
new DataMemberModelValidatorProvider()
}
ValidatorProvider = new CompositeModelValidatorProvider(provider.Object)
};
}
private static IModelValidator GetRequiredValidator(ModelBindingContext bindingContext, ModelMetadata propertyMetadata)
{
return bindingContext.ValidatorProviders
.SelectMany(v => v.GetValidators(propertyMetadata))
.Where(v => v.IsRequired)
.FirstOrDefault();
return bindingContext.ValidatorProvider
.GetValidators(propertyMetadata)
.FirstOrDefault(v => v.IsRequired);
}
private static ModelMetadata GetMetadataForCanUpdateProperty(string propertyName)
{
DataAnnotationsModelMetadataProvider metadataProvider = new DataAnnotationsModelMetadataProvider();
var metadataProvider = new DataAnnotationsModelMetadataProvider();
return metadataProvider.GetMetadataForProperty(null, typeof(MyModelTestingCanUpdateProperty), propertyName);
}
private static ModelMetadata GetMetadataForObject(object o)
{
DataAnnotationsModelMetadataProvider metadataProvider = new DataAnnotationsModelMetadataProvider();
var metadataProvider = new DataAnnotationsModelMetadataProvider();
return metadataProvider.GetMetadataForType(() => o, o.GetType());
}
private static ModelMetadata GetMetadataForType(Type t)
{
DataAnnotationsModelMetadataProvider metadataProvider = new DataAnnotationsModelMetadataProvider();
var metadataProvider = new DataAnnotationsModelMetadataProvider();
return metadataProvider.GetMetadataForType(null, t);
}

View File

@ -0,0 +1,41 @@
// 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 Moq;
using Xunit;
namespace Microsoft.AspNet.Mvc.ModelBinding.Test
{
public class CompositeModelValidatorProviderTest
{
[Fact]
public void GetModelValidators_ReturnsValidatorsFromAllProviders()
{
// Arrange
var validator1 = Mock.Of<IModelValidator>();
var validator2 = Mock.Of<IModelValidator>();
var validator3 = Mock.Of<IModelValidator>();
var provider1 = new Mock<IModelValidatorProvider>();
provider1.Setup(p => p.GetValidators(It.IsAny<ModelMetadata>()))
.Returns(new[] { validator1, validator2 });
var provider2 = new Mock<IModelValidatorProvider>();
provider2.Setup(p => p.GetValidators(It.IsAny<ModelMetadata>()))
.Returns(new[] { validator3 });
var providerProvider = new Mock<IModelValidatorProviderProvider>();
providerProvider.Setup(p => p.ModelValidatorProviders)
.Returns(new[] { provider1.Object, provider2.Object });
var compositeModelValidator = new CompositeModelValidatorProvider(providerProvider.Object);
var modelMetadata = new EmptyModelMetadataProvider().GetMetadataForType(
modelAccessor: null,
modelType: typeof(string));
// Act
var result = compositeModelValidator.GetValidators(modelMetadata);
// Assert
Assert.Equal(new[] { validator1, validator2, validator3 }, result);
}
}
}
#endif

View File

@ -1,10 +1,12 @@
// 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.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.Linq;
using Microsoft.AspNet.Testing;
using Moq;
using Xunit;
namespace Microsoft.AspNet.Mvc.ModelBinding
@ -294,8 +296,12 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
new DataMemberModelValidatorProvider()
};
var provider = new Mock<IModelValidatorProviderProvider>();
provider.SetupGet(p => p.ModelValidatorProviders)
.Returns(providers);
return new ModelValidationContext(new EmptyModelMetadataProvider(),
providers,
new CompositeModelValidatorProvider(provider.Object),
new ModelStateDictionary(),
metadata,
null);
@ -343,4 +349,5 @@ namespace Microsoft.AspNet.Mvc.ModelBinding
public string ValidString { get; set; }
}
}
}
}
#endif

View File

@ -97,5 +97,21 @@ namespace Microsoft.AspNet.Mvc
Assert.IsType<XmlSerializerInputFormatter>(mvcOptions.InputFormatters[1].Instance);
Assert.IsType<XmlDataContractSerializerInputFormatter>(mvcOptions.InputFormatters[2].Instance);
}
[Fact]
public void Setup_SetsUpModelValidatorProviders()
{
// Arrange
var mvcOptions = new MvcOptions();
var setup = new MvcOptionsSetup();
// Act
setup.Setup(mvcOptions);
// Assert
Assert.Equal(2, mvcOptions.ModelValidatorProviders.Count);
Assert.IsType<DataAnnotationsModelValidatorProvider>(mvcOptions.ModelValidatorProviders[0].Instance);
Assert.IsType<DataMemberModelValidatorProvider>(mvcOptions.ModelValidatorProviders[1].Instance);
}
}
}