سؤال

I made test attribute

    [AttributeUsageAttribute(AttributeTargets.Property | AttributeTargets.Field, Inherited = false)]
    public class NonInheritedRequiredAttribute : ValidationAttribute
    {
        protected override ValidationResult IsValid(object value, ValidationContext validationContext)
        {
            if (value == null)
                return new ValidationResult((validationContext.DisplayName));
            return null;
        }
    }

And viewModels

    public class ViewModelA
    {
        [NonInheritedRequired]
        public virtual string Property{ get; set; }
    }

    public class ViewModelB : ViewModelA
    {
        public override string Property{ get; set; }
    }

Action method

        [HttpPost]
        public ActionResult Index(ViewModelB viewModel)
        {
            if (ModelState.IsValid)
            {
                return View("OtherView");
            }

            return View(viewModel);
        }

ModelState always is not valid. On validating it uses validation of NonInheritedRequired despite it has Inherited = false. How can I solve this problem?

Thanks.

هل كانت مفيدة؟

المحلول

The Inherited property isn't respected in MVC.

possible solutions:

  1. Implement a custom ModelValidatorProvider which will filter out non inheritable validation attributes.

  2. Filter out non inheritable attributes by providing a custom TypeDescriptionProvider

  3. Use MetadataType attribute in your models. This is the easiest of all.

Sample

[MetadataType(typeof(ModelAMetadata))]
public class ModelA
{
    public virtual string Property { get; set; }
}

public class ModelAMetadata
{
    [Required]
    public string Property { get; set; }
}

[MetadataType(typeof(ModelBMetadata))]
public class ModelB : ModelA
{
    public override string Property { get; set; }
}

public class ModelBMetadata
{
    //notice that there is no Required attribute here
    public string Property { get; set; }
}

Most elegant solution is #1, but I suggest to redesign the Models instead.

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top