Question

J'utilise Ninject, MVC4, Automapper et FluentValidation collé ensemble.

J'ai écrit un validateur pour mon modèle de vue et j'ai écrit un validateur réutilisable qui doit être invoqué dans le validateur du modèle de vue.

Le problème est que lorsque je publie le formulaire, le remplacement de validate n'est pas appelé sur le validateur du modèle de vue, donc le validateur réutilisable n'est pas non plus appelé, donc à la fin le ModelResult est valide ... (provoquant une exception lors de l'écriture de l'entité à la base de données) ...

Ce qui est étrange, c'est que lorsque j'ai ajouté une règle pour l'une des propriétés, le formulaire est bien validé.

public class RequiredSourceViewModelValidator : AbstractValidator<RequiredSourceViewModel>
    {
        public RequiredSourceViewModelValidator()
        {
            Mapper.CreateMap<RequiredSourceViewModel, Source>();
        }

        public override FluentValidation.Results.ValidationResult Validate(RequiredSourceViewModel requiredSourceViewModel)
        {
            var validator = new SourceValidator();

            var source = Mapper.Map<RequiredSourceViewModel, Source>(requiredSourceViewModel);

            return validator.Validate(source);
        }
    }


public class SourceValidator : AbstractValidator<Source>
    {
        public SourceValidator()
        {
            RuleFor(s => s.Name)
                .NotEmpty()
                    .WithMessage("Naam mag niet leeg zijn.")
                .Length(1, 100)
                    .WithMessage("Naam mag niet langer zijn dan 100 karakters.");

            RuleFor(s => s.Url)
                .NotEmpty()
                    .WithMessage("Url mag niet leeg zijn.")
                 .Must(BeAValidUrl)
                    .WithMessage("Url is niet geldig.")
                .Length(1, 100)
                    .WithMessage("Url mag niet langer zijn dan 100 karakters.");
        }

        private bool BeAValidUrl(string url)
        {
            if (url == null)
            {
                return true;
            }

            var regex = new Regex(@"^http(s)?://([\w-]+.)+[\w-]+(/[\w- ./?%&=])?$");
            return regex.IsMatch(url);
        }
    }

public class Source : IEntity
    {
        /// <summary>
        /// Gets or sets the primary key of the source.
        /// </summary>
        public int Id { get; set; }

        /// <summary>
        /// Gets or sets the name of the source.
        /// </summary>
        public string Name { get; set; }

        /// <summary>
        /// Gets or sets the url of the source.
        /// </summary>
        public string Url { get; set; }

        /// <summary>
        /// Gets or sets the ordinal of the source.
        /// </summary>
        /// <value>
        /// The ordinal of the source.
        /// </value>
        public int Ordinal { get; set; }

        public int? GameId { get; set; }
    }

Qu'est-ce qui pourrait ne pas être mal ici?

Était-ce utile?

La solution

Vous remplacez la mauvaise surcharge. Vous devez remplacer la méthode Validate avec la signature: public virtual ValidationResult Validate(ValidationContext<T> context) Parce que cette méthode sera appelée pendant la validation MVC:

public override ValidationResult Validate(
      ValidationContext<RequiredSourceViewModel> context)
{
     var validator = new SourceValidator();

     var source = 
         Mapper.Map<RequiredSourceViewModel, Source>(context.InstanceToValidate);

     return validator.Validate(source);
 }

L'autre surcharge n'est utilisée que si vous appelez manuellement valider comme validator.Validate(object).

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top