我想根据另一个属性的值使用数据注释验证属性。
我有一个人模型 -
public class People
{
[DisplayName("Your Name")]
[Required]
public string Name { get; set; }
[Required]
public string Gender { get; set; }
[DisplayName("Your Age")]
[Required]
// Another Attribute here for my custom validation
public int Age { get; set; }
}
和指数:
public ActionResult Index()
{
IList<SelectListItem> types = new List<SelectListItem>();
types.Add(new SelectListItem() { Text = "Male", Value = "M" });
types.Add(new SelectListItem() { Text = "Female", Value = "F" });
ViewBag.ItemTypes = types;
return View();
}
&#39;性别&#39;被绑定到下拉列表,并根据我想要验证的所选性别&#39;年龄&#39;属性。
必须有一个自定义验证属性,但我无法弄明白。
我的观点:
@using (Html.BeginForm("Index", "Test", FormMethod.Post))
{
@Html.AntiForgeryToken()
<div class="form-horizontal">
<h4>TimeRecord</h4>
<hr />
@Html.ValidationSummary(true, "", new { @class = "text-danger" })
<div class="form-group">
@Html.LabelFor(model => model.Gender, htmlAttributes: new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.DropDownListFor(model => model.Gender, (IEnumerable<SelectListItem>)ViewBag.ItemTypes, new { @class = "form-control" })
</div>
</div>
<div class="form-group">
@Html.LabelFor(m => m.Name, new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.TextBoxFor(m => m.Name, new { @class = "form-control" })
@Html.ValidationMessageFor(m => m.Name, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
@Html.LabelFor(m => m.Age, new { @class = "control-label col-md-2" })
<div class="col-md-10">
@Html.TextBoxFor(m => m.Age, new { @class = "form-control" })
@Html.ValidationMessageFor(m => m.Age, "", new { @class = "text-danger" })
</div>
</div>
<div class="form-group">
<div class="col-md-offset-2 col-md-10">
<input type="submit" value="Create" class="btn btn-default" />
</div>
</div>
</div>
}
答案 0 :(得分:2)
您可以创建自定义验证属性,因为它可以很好地验证各个属性(单个属性级别验证),请查看以下代码段。
namespace SO.Models
{
using Helpers;
using System.ComponentModel;
using System.ComponentModel.DataAnnotations;
public class Person
{
// code omitted for brevity
[DisplayName("Your Age")]
[Required]
[PersonAge(minMaleAge: 22, maxMaleAge: 60, minFemaleAge: 18, maxFemaleAge: 58)]
public int Age { get; set; }
}
}
namespace SO.Helpers
{
using Models;
using System.ComponentModel.DataAnnotations;
public class PersonAgeAttribute : ValidationAttribute
{
private const string _validationMessage = "Age should be between {0} and {1}";
private int _minMaleAge;
private int _maxMaleAge;
private int _minFemaleAge;
private int _maxFemaleAge;
public PersonAgeAttribute(int minMaleAge, int maxMaleAge, int minFemaleAge, int maxFemaleAge)
{
_minMaleAge = minMaleAge;
_maxMaleAge = maxMaleAge;
_minFemaleAge = minFemaleAge;
_maxFemaleAge = maxFemaleAge;
}
protected override ValidationResult IsValid(object value, ValidationContext validationContext)
{
Person person = (Person)validationContext.ObjectInstance;
if (person.Gender == "M" && (person.Age < _minMaleAge || person.Age > _maxMaleAge))
{
return new ValidationResult(GetErrorMessage(person.Gender));
}
else if (person.Gender == "F" && (person.Age < _minFemaleAge || person.Age > _maxFemaleAge))
{
return new ValidationResult(GetErrorMessage(person.Gender));
}
return ValidationResult.Success;
}
private string GetErrorMessage(string gender)
{
if (gender == "M")
{
return string.Format(_validationMessage, _minMaleAge, _maxMaleAge);
}
else
{
return string.Format(_validationMessage, _minFemaleAge, _maxFemaleAge);
}
}
}
}
或者IValidatableObject
接口可以通过实现其Validate
方法来实现类级验证。有关详细信息,请查看Class-Level Model Validation
答案 1 :(得分:0)
根据您的要求,根据我的理解,解决方案可能是这样的。
对于服务器端验证,请创建自己的自定义验证属性。要启用客户端验证,请继承“IClientValidatable”。
[AttributeUsage(AttributeTargets.Property, AllowMultiple = true, Inherited = false)]
public class AgeForGenderAttribute : ValidationAttribute, IClientValidatable
{
private string _PropertyToCompare { get; set; }
private string CurrentPropertyValue { get; set; }
public int _MinAgeForMale { get; set; }
public int _MaxAgeForMale { get; set; }
public int _MinAgeForFemale { get; set; }
public int _MaxAgeForFemale { get; set; }
string relevantErrorMessage { get; set; }
public AgeForGenderAttribute(string PropertyToCompare, int MinAgeForMale, int MaxAgeForMale, int MinAgeForFemale, int MaxAgeForFemale, string validationMessage)
{
this._PropertyToCompare = PropertyToCompare;
this._MinAgeForMale = MinAgeForMale;
this._MaxAgeForMale = MaxAgeForMale;
this._MinAgeForFemale = MinAgeForFemale;
this._MaxAgeForFemale = MaxAgeForFemale;
ErrorMessage = validationMessage;
}
protected override ValidationResult IsValid(object value, ValidationContext validationContext)
{
var comparePropertyInfo = validationContext.ObjectType.GetProperty(_PropertyToCompare);
object dependentPropertyValue = comparePropertyInfo.GetValue(validationContext.ObjectInstance, null);
CurrentPropertyValue = dependentPropertyValue.ToString();
var currentValue = (int)value;
if (dependentPropertyValue != null)
{
switch (CurrentPropertyValue)
{
case "M":
if (currentValue < _MinAgeForMale || currentValue > _MaxAgeForMale)
{
ErrorMessage = string.Format(ErrorMessage, _MinAgeForMale, _MaxAgeForMale);
return new ValidationResult(ErrorMessage);
}
break;
case "F":
if (currentValue < _MinAgeForFemale || currentValue > _MaxAgeForFemale)
{
ErrorMessage = string.Format(ErrorMessage, _MinAgeForMale, _MaxAgeForMale);
return new ValidationResult(ErrorMessage);
}
break;
}
}
return ValidationResult.Success;
}
public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
{
var rules = new ModelClientValidationRule
{
ValidationType = "conditionalrange",
ErrorMessage = ErrorMessage
};
rules.ValidationParameters.Add("condiotionalpropertyname", _PropertyToCompare);
rules.ValidationParameters.Add("minageformale", _MinAgeForMale);
rules.ValidationParameters.Add("maxageformale", _MaxAgeForMale);
rules.ValidationParameters.Add("minageforfemale", _MinAgeForFemale);
rules.ValidationParameters.Add("maxageforfemale", _MaxAgeForFemale);
yield return rules;
}
}
你的js:
$(function () {
$.validator.addMethod("conditionalrange", function (value, element, params) {
var condiotionalpropertyname = $('#' + params.condiotionalpropertyname).val();
var retVal = true;
switch (condiotionalpropertyname) {
case 'M':
if (value < params.minageformale || value > params.maxageformale) {
retVal = false;
}
break;
case "F":
if (value < params.minageforfemale || value > params.maxageforfemale) {
retVal = false;
}
break;
}
return retVal;
});
$.validator.unobtrusive.adapters.add("conditionalrange", ['condiotionalpropertyname', 'minageformale', 'maxageformale', 'minageforfemale', 'maxageforfemale'],
function (options) {
options.rules['conditionalrange'] = {
condiotionalpropertyname: options.params.condiotionalpropertyname,
minageformale: options.params.minageformale,
maxageformale: options.params.maxageformale,
minageforfemale: options.params.minageforfemale,
maxageforfemale: options.params.maxageforfemale
};
options.messages['conditionalrange'] = options.message;
}
);
}(jQuery));
它将完全按照您的要求工作。确保您已包含所有相关的j。
属性:
[DisplayName("Your Age")]
[Required]
[AgeForGender("Gender", 18, 45, 22, 60, "Age should be between {0} and {1}")]
public int Age { get; set; }