【问题标题】:FluentValidation.Net doesn't produce client side unobtrusive validation when using .SetValidator()FluentValidation.Net 在使用 .SetValidator() 时不会产生客户端不显眼的验证
【发布时间】:2012-01-31 11:12:24
【问题描述】:

我正在尝试让客户端验证适用于使用编辑器模板的页面。

我的视图模型的简化示例例如:

[Validator(typeof(ValidationTestModelValidator))]
public class ValidationTestModel
{
    public string Name { get; set; }

    public string Age { get; set; }

    public ChildModel Child { get; set; }
}

子模型例如:

public class ChildModel
{
    public string ChildName { get; set; }

    public string ChildAge { get; set; }
}

我的验证器是例如:

public class ValidationTestModelValidator : AbstractValidator<ValidationTestModel>
{
    public ValidationTestModelValidator()
    {
        RuleFor(m => m.Name)
            .NotEmpty()
            .WithMessage("Please enter the name");

        RuleFor(m => m.Age)
            .NotEmpty()
            .WithMessage("Please enter the age");

        RuleFor(m => m.Age)
            .Matches(@"\d*")
            .WithMessage("Must be a number");

        RuleFor(m => m.Child)
            .SetValidator(new ChildModelValidator());
    }
}

子模型验证器是例如:

public class ChildModelValidator : AbstractValidator<ChildModel>
{
    public ChildModelValidator()
    {
        RuleFor(m => m.ChildName)
            .NotEmpty()
            .WithMessage("Please enter the name");

        RuleFor(m => m.ChildAge)
            .NotEmpty()
            .WithMessage("Please enter the age");

        RuleFor(m => m.ChildAge)
            .Matches(@"\d*")
            .WithMessage("Must be a number");
    }
}

我通过将以下内容添加到 Application_Start() 中,向 MVC3 注册了 FluentValidation.Net:

// Register FluentValidation.Net
FluentValidationModelValidatorProvider.Configure();

这会为 Name 和 Age 这两个属性完美地生成不显眼的客户端验证,但不会为 ChildModel 上的属性生成任何内容。

有什么想法我在这里做错了吗?

更新:如果我只是用 Validator 属性注释 ChildModel 似乎可以正常工作,但是我想有条件地应用验证,因此使用 SetValidator()。

【问题讨论】:

  • RuleFor 这是来自 mvc 库还是外部库?如果是外部的,您使用的是哪一个?
  • @DarthVader:来自FluentValidation

标签: asp.net-mvc-3 fluentvalidation


【解决方案1】:

我试图分析文档http://fluentvalidation.codeplex.com/wikipage?title=mvc&referringTitle=Documentation。它指出 MVC 集成默认基于属性工作,因为它的验证器工厂使用属性来实例化适当的验证器。显然它确实验证了主模型上的属性引用的 ChildModel,但这可能只是模型结构的自动递归遍历以生成客户端验证代码。因此它可能使用相同的机制来为 ChildModel 类型定位适当的验证器。您能否测试如果删除 SetValidator 规则(但保留 ChildModel 的属性)会发生什么,它是否仍会根据该属性生成验证器?

有一个明确的客户端支持的验证器列表,但不幸的是,那里没有提到(或解释)SetValidator,这是一个不好的迹象。

该文档还指出客户端不支持使用条件的规则,因此很可能您无法使用 SetValidator 解决此问题(如您在更新中所述)。

另请参阅有关客户端条件规则的讨论:http://fluentvalidation.codeplex.com/discussions/393596。建议使用 jQuery Validation 在 JS 中实现条件规则,但是,如果您有一个应该有条件地添加的复杂验证,这可能会很复杂。

让它添加带有属性的验证器,但之后以某种方式抑制它们怎么样?例如。之后从元素中删除不显眼的属性?

【讨论】:

    【解决方案2】:

    正如您在更新中指出的那样,如果您想发出不显眼的标记,则需要使用验证器装饰子类型。然后,您可以通过包装在 if 块中或使用 FluentValidation 的 When() 方法来使用表达式,在“父”验证器类中有条件地使用它。

    另外,请注意,您还可以为属性链接规则(即使用流畅的界面):

    RuleFor(m => m.ChildName)
        .NotEmpty()
        .WithMessage("Please enter the name")
        .Matches(@"\d*")
        .WithMessage("Must be a number");
    

    【讨论】:

      【解决方案3】:

      如果其他人有同样的问题:

      您还需要在 ChildModel 上添加验证器属性

      [Validator(typeof(ChildModelValidator))]
      public class ChildModel
      

      并保持所有其他代码不变,然后它在客户端工作

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2011-07-22
        • 2021-02-19
        • 1970-01-01
        • 1970-01-01
        • 2011-05-10
        • 1970-01-01
        • 2012-07-11
        相关资源
        最近更新 更多