我正在使用http://fluentvalidation.codeplex.com/来验证某些域模型。
我有一个典型的场景,我想验证一个字符串,例如......
RuleFor(x => x.MyString).NotNull().NotEmpty().Length(2, 20).WithMessage("Please provide a string with a minium of 2 characters.");
...在我创建一个单元测试之前,所有工作都很好用,指定MyString属性的长度必须为2-20个字符 不 < em>包括空格。
因此myObject.myString = "A" + new String(' ', 10);
验证失败。
我可以使用.Must(IsValidString)
完成所有这些操作,并将自己的所有逻辑写入...
private bool IsValidString(string myString)
{
if(String.IsNullOrEmpty(myString))
return false;
// Then work on myString.Trim()'ed value.
}
...但随后我放弃了所有可爱的流利验证!!
显然我可以使用这种方法让我的单元测试通过,所有人都会在我的小世界中感到高兴,但我错过了一个技巧吗?
非常感谢。
答案 0 :(得分:4)
使用http://ilspy.net/稍微查看dll FluentValidation dll,我就能获得灵感来制作以下TrimmedLengthValidator ......
public static class DefaultValidatorExtensions
{
public static IRuleBuilderOptions<T, string> TrimmedLength<T>(this IRuleBuilder<T, string> ruleBuilder, int min, int max)
{
return ruleBuilder.SetValidator(new TrimmedLengthValidator(min, max));
}
}
public class TrimmedLengthValidator : PropertyValidator, ILengthValidator, IPropertyValidator
{
public int Min { get; private set; }
public int Max { get; private set; }
public TrimmedLengthValidator(int min, int max)
: this(min, max, () => Messages.length_error)
{ }
public TrimmedLengthValidator(int min, int max, Expression<Func<string>> errorMessageResourceSelector)
: base(errorMessageResourceSelector)
{
this.Max = max;
this.Min = min;
if (max != -1 && max < min)
throw new ArgumentOutOfRangeException("max", "Max should be larger than min.");
}
protected override bool IsValid(PropertyValidatorContext context)
{
if (context.PropertyValue == null)
return true;
int length = context.PropertyValue.ToString().Trim().Length;
if (length < this.Min || (length > this.Max && this.Max != -1))
{
context.MessageFormatter.AppendArgument("MinLength", this.Min).AppendArgument("MaxLength", this.Max).AppendArgument("TotalLength", length);
return false;
}
return true;
}
}
...这意味着我可以简单地将我的验证更改为:
RuleFor(x => x.myString).NotEmpty().TrimmedLength(2, 20).WithMessage("Please provide a string with a minium of 2 characters.");
摇滚!
答案 1 :(得分:1)
我对这个框架并不熟悉,但这样的工作会不会这样? 你仍然可以保持大部分的流利程度,但检查空格需要你编写自定义验证器(这是一个很大的麻烦),或者使用Predicate验证器
RuleFor(x => x.MyString)
.NotNull()
.NotEmpty()
.Length(2, 20)
.WithMessage("Please provide a string with a minium of 2 characters.")
.Must(myString => myString == Regex.Replace( myString, @"s", "" ))
答案 2 :(得分:0)
RuleFor(x => x.myStringBefore).Transform(c => c.Trim()).NotEmpty();
使用转换
您可以使用修剪或子字符串...(转换后)流利验证允许 将任何有效规则应用于转换后的值。
答案 3 :(得分:0)
在验证前使用 Transform 准备值:
版本:9.5+
Transform(i => i.InitialString, v => v?.Trim()).NotEmpty();
版本:9.0 - 9.4:
RuleFor(x => x.InitialString).Transform(v => v?.Trim()).NotEmpty();