Esempio n. 1
0
        private bool ValidateProperties(
            string currentModelKey,
            ModelExplorer modelExplorer,
            ValidationContext validationContext)
        {
            var isValid = true;

            foreach (var property in modelExplorer.Metadata.Properties)
            {
                var propertyExplorer          = modelExplorer.GetExplorerForProperty(property.PropertyName);
                var propertyMetadata          = propertyExplorer.Metadata;
                var propertyValidationContext = new ValidationContext()
                {
                    ModelValidationContext = ModelValidationContext.GetChildValidationContext(
                        validationContext.ModelValidationContext,
                        propertyExplorer),
                    Visited = validationContext.Visited
                };

                var propertyBindingName = propertyMetadata.BinderModelName ?? propertyMetadata.PropertyName;
                var childKey            = ModelBindingHelper.CreatePropertyModelName(currentModelKey, propertyBindingName);
                if (!ValidateNonVisitedNodeAndChildren(
                        childKey,
                        propertyValidationContext,
                        validators: null))
                {
                    isValid = false;
                }
            }

            return(isValid);
        }
Esempio n. 2
0
        // Validates a single node (not including children)
        // Returns true if validation passes successfully
        private static bool ShallowValidate(
            string modelKey,
            ModelExplorer modelExplorer,
            ValidationContext validationContext,
            IList <IModelValidator> validators)
        {
            var isValid = true;

            var modelState           = validationContext.ModelValidationContext.ModelState;
            var fieldValidationState = modelState.GetFieldValidationState(modelKey);

            if (fieldValidationState == ModelValidationState.Invalid)
            {
                // Even if we have no validators it's possible that model binding may have added a
                // validation error (conversion error, missing data). We want to still run
                // validators even if that's the case.
                isValid = false;
            }

            // When the are no validators we bail quickly. This saves a GetEnumerator allocation.
            // In a large array (tens of thousands or more) scenario it's very significant.
            if (validators == null || validators.Count > 0)
            {
                var modelValidationContext = ModelValidationContext.GetChildValidationContext(
                    validationContext.ModelValidationContext,
                    modelExplorer);

                var modelValidationState = modelState.GetValidationState(modelKey);

                // If either the model or its properties are unvalidated, validate them now.
                if (modelValidationState == ModelValidationState.Unvalidated ||
                    fieldValidationState == ModelValidationState.Unvalidated)
                {
                    foreach (var validator in validators)
                    {
                        foreach (var error in validator.Validate(modelValidationContext))
                        {
                            var errorKey = ModelBindingHelper.CreatePropertyModelName(modelKey, error.MemberName);
                            if (!modelState.TryAddModelError(errorKey, error.Message) &&
                                modelState.GetFieldValidationState(errorKey) == ModelValidationState.Unvalidated)
                            {
                                // If we are not able to add a model error
                                // for instance when the max error count is reached, mark the model as skipped.
                                modelState.MarkFieldSkipped(errorKey);
                            }

                            isValid = false;
                        }
                    }
                }
            }

            if (isValid)
            {
                validationContext.ModelValidationContext.ModelState.MarkFieldValid(modelKey);
            }

            return(isValid);
        }
Esempio n. 3
0
        private bool ValidateElements(string currentKey, IEnumerable model, ValidationContext validationContext)
        {
            var elementType     = GetElementType(model.GetType());
            var elementMetadata = _modelMetadataProvider.GetMetadataForType(elementType);

            var validatorProvider        = validationContext.ModelValidationContext.ValidatorProvider;
            var validatorProviderContext = new ModelValidatorProviderContext(elementMetadata);

            validatorProvider.GetValidators(validatorProviderContext);

            var validators = validatorProviderContext.Validators;

            // If there are no validators or the object is null we bail out quickly
            // when there are large arrays of null, this will save a significant amount of processing
            // with minimal impact to other scenarios.
            var anyValidatorsDefined = validators.Any();
            var index   = 0;
            var isValid = true;

            foreach (var element in model)
            {
                // If the element is non null, the recursive calls might find more validators.
                // If it's null, then a shallow validation will be performed.
                if (element != null || anyValidatorsDefined)
                {
                    var elementExplorer          = new ModelExplorer(_modelMetadataProvider, elementMetadata, element);
                    var elementKey               = ModelBindingHelper.CreateIndexModelName(currentKey, index);
                    var elementValidationContext = new ValidationContext()
                    {
                        ModelValidationContext = ModelValidationContext.GetChildValidationContext(
                            validationContext.ModelValidationContext,
                            elementExplorer),
                        Visited = validationContext.Visited
                    };

                    if (!ValidateNonVisitedNodeAndChildren(elementKey, elementValidationContext, validators))
                    {
                        isValid = false;
                    }
                }

                index++;
            }

            return(isValid);
        }
Esempio n. 4
0
        private bool ValidateChildNodes(
            string currentModelKey,
            ModelExplorer modelExplorer,
            ValidationContext validationContext)
        {
            var isValid = true;

            ExpandValidationNode(validationContext, modelExplorer);

            IList <IModelValidator> validators = null;

            if (modelExplorer.Metadata.IsCollectionType && modelExplorer.Model != null)
            {
                var enumerableModel = (IEnumerable)modelExplorer.Model;
                var elementType     = GetElementType(enumerableModel.GetType());
                var elementMetadata = _modelMetadataProvider.GetMetadataForType(elementType);
                validators = GetValidators(validationContext.ModelValidationContext.ValidatorProvider, elementMetadata);
            }

            foreach (var childNode in validationContext.ValidationNode.ChildNodes)
            {
                var childModelExplorer = childNode.ModelMetadata.MetadataKind == Metadata.ModelMetadataKind.Type ?
                                         _modelMetadataProvider.GetModelExplorerForType(childNode.ModelMetadata.ModelType, childNode.Model) :
                                         modelExplorer.GetExplorerForProperty(childNode.ModelMetadata.PropertyName);

                var propertyValidationContext = new ValidationContext()
                {
                    ModelValidationContext = ModelValidationContext.GetChildValidationContext(
                        validationContext.ModelValidationContext,
                        childModelExplorer),
                    Visited        = validationContext.Visited,
                    ValidationNode = childNode
                };

                if (!ValidateNonVisitedNodeAndChildren(
                        childNode.Key,
                        propertyValidationContext,
                        validators))
                {
                    isValid = false;
                }
            }

            return(isValid);
        }