流利的验证不适用于异常

Fluent Validation not working on Exception

ServiceStack 升级到 4.5.8 后,ServiceStack 会吃掉 Fluent Validation 抛出的异常并通过验证,而不是在验证器内部抛出异常时失败。这似乎只发生在验证器 运行 使用 SetValidator 方法时。

这将 return 新用户而不是 return 发送错误消息 "Validator Exception"。

验证者

public class SaveUserValidator : AbstractValidator<SaveUser>
{
    public SaveUserValidator()
    {
        this.CascadeMode = CascadeMode.StopOnFirstFailure;

        RuleFor(x => x.Id)
            .Must(ThrowException);

        RuleFor(x => x.User)
            .SetValidator(new UserValidator());
    }

    private bool ThrowException(int arg)
    {
        throw new ApplicationException("Validator Exception");
    }
}

用户验证器

public class UserValidator : AbstractValidator<User>
{
    public UserValidator()
    {
        this.CascadeMode = CascadeMode.StopOnFirstFailure;

        RuleFor(x => x.Name).NotEmpty();
    }
}

用户

public class User
{
    public string Name { get; set; }
}

保存用户

public class SaveUser
{
    public int Id { get; set; }

    public User User { get; set; }
}

用户服务

public class UserService : Service
{
    public IHttpResult Post(SaveUser request)
    {
        return new HttpResult(new SaveUser { Id = -100, User = new User { Name = "bad name" } }, HttpStatusCode.Created);
    }
}

ServiceStack 升级为使用 v4.5.8 中的 latest version of FluentValidation,发行说明中概述的更改之一随 Fluent Validation 发生了变化,因为之前的版本必须明确指定不应为 null 的属性,所以您的 UserValidator 应该更改为:

RuleFor(x => x.User)
    .NotEmpty()
    .SetValidator(new UserValidator());

吞噬异常的问题是由于 ChildValidatorAdaptor 被异步处理并且抛出的异常未被处理,因为像 Must() 这样的验证异常应该 return 一个 boolean 如果 属性 验证失败,例如:

RuleFor(x => x.Id)
    .Must(id => false);

不抛出异常,但我刚刚在 this commit. This change is available from v4.5.13 that's now available on MyGet.

中添加了对处理验证器中抛出的异常的支持