【问题标题】:SetValidator for complex properties not working复杂属性的 SetValidator 不起作用
【发布时间】:2013-09-11 18:11:45
【问题描述】:

我有以下“费用”实体的验证类:

public class ExpenseBaseValidator : AbstractValidator<Expense>
{
    public ExpenseBaseValidator()
    {
        RuleFor(x => x.Description).NotEmpty();
        RuleFor(x => x.Amount).NotNull();
        RuleFor(x => x.BusinessID).NotEqual(0).WithMessage("BusinessID is required.");
        RuleFor(x => x.ExpenseTypeID).NotEqual(0).WithMessage("ExpenseTypeID is required.");
        RuleFor(x => x.CreatedDate).NotNull();
        RuleFor(x => x.Transaction).SetValidator(new TransactionValidator());
    }
}

然后我有 Transaction 的验证类,这是上面 Expense 类中的一个复杂属性:

public class TransactionBaseValidator : AbstractValidator<Transaction>
{
    public TransactionBaseValidator()
    {
        RuleFor(x => x.BankAccountID).NotEqual(0).WithMessage("BankAccountID is required.");
        RuleFor(x => x.EmployeeID).NotEqual(0).WithMessage("EmployeeID is required.");
        RuleFor(x => x.TransactionDate).NotNull();
        RuleFor(x => x.IsWithdrawal).NotNull();
        RuleFor(x => x.Amount).NotNull();
        RuleFor(x => x.Description).NotEmpty();
        RuleFor(x => x.PaymentMethod).NotEmpty();
        RuleFor(x => x.PaymentMethod).Length(0, 50).WithMessage("PaymentMethod can not exceed 50 characters");
    }
}

现在这些是基类,我分别使用以下子类调用验证器:

public class ExpenseValidator : ExpenseBaseValidator
{
    public ExpenseValidator()
        : base()
    {
        RuleFor(x => x.Transaction)
            .NotNull()
            .When(x => x.IsPaid == true)
            .WithMessage("An account transaction is required when the amount is paid.");

        RuleFor(x => x.DatePaid)
            .NotNull()
            .When(x => x.IsPaid == true)
            .WithMessage("Please enter the date when the expense was paid.");
    }
}

和Transaction子类:

public class TransactionValidator : TransactionBaseValidator
{
    public TransactionValidator() : base()
    {

    }
}

这些可以有额外的验证规则,并且使用base()构造函数调用基本规则。

我使用这个验证 Expense 对象:

var validator = new ExpenseValidator();
var results = validator.Validate(oExpense);

现在这不会返回对我以下列方式使用的复杂属性事务的验证:

oExpense.Transaction = new Transaction();
oExpense.Transaction.Amount = oExpense.Amount;
oExpense.Transaction.BankAccountID = ddlAccounts.SelectedItem.Value.ToInt();
oExpense.Transaction.TransactionDate = oExpense.DatePaid.Value;
oExpense.Transaction.IsWithdrawal = true;
oExpense.Transaction.Description = oExpense.Description;
oExpense.Transaction.IsDeleted = false;
// I dont set the below and it should give me validation error:
// oExpense.Transaction.EmployeeID = 10;

我没有设置 EmployeeID,当我为费用对象调用验证器时它应该给我验证错误,因为它有 SetValidator() 用于 Transaction 属性,并且 Transaction 也不为空,因为我已经设置了 new Transaction()

有什么想法吗?

【问题讨论】:

    标签: c# fluentvalidation


    【解决方案1】:

    我使用了您发布的验证,并根据验证器中包含的内容创建了相关的类/属性。从发布的示例中构建 Transaction 对象,我收到以下验证错误:

    • “描述”不应为空。
    • “金额”不能为空。
    • BusinessID 为必填项。
    • ExpenseTypeID 为必填项。
    • EmployeeID 是必填项。
    • “金额”不能为空。
    • “描述”不应为空。
    • “付款方式”不能为空。

    var results = validator.Validate(oExpense); 上放置断点并验证oExpense.Transaction.EmployeeID 的值。 如果值不为 0,则 EmployeeID 被设置在其他位置。

    作为参考,这是我创建的基本控制台应用程序:

    using System;
    using System.Linq;
    using FluentValidation;
    using FluentValidation.Results;
    
    namespace so.FluentValidationComplexProperties
    {
        internal class Program
        {
            private static void Main( string[] args )
            {
                var oExpense = new Expense();
                oExpense.Transaction = new Transaction();
                oExpense.Transaction.Amount = oExpense.Amount;
                oExpense.Transaction.BankAccountID = 10;
                oExpense.Transaction.TransactionDate = DateTime.Today;
                oExpense.Transaction.IsWithdrawal = true;
                oExpense.Transaction.Description = oExpense.Description;
                oExpense.Transaction.IsDeleted = false;
                // I dont set the below and it should give me validation error:
                // oExpense.Transaction.EmployeeID = 10;
    
    
                var validator = new ExpenseValidator();
                ValidationResult results = validator.Validate( oExpense );
    
                results.Errors.ToList().ForEach( Console.WriteLine );
    
                Console.WriteLine();
                Console.Write( "--done--" );
                Console.WriteLine();
                Console.ReadLine();
            }
        }
    
    
        public class ExpenseBaseValidator : AbstractValidator<Expense>
        {
            public ExpenseBaseValidator()
            {
                RuleFor( x => x.Description ).NotEmpty();
                RuleFor( x => x.Amount ).NotNull();
                RuleFor( x => x.BusinessID ).NotEqual( 0 ).WithMessage( "BusinessID is required." );
                RuleFor( x => x.ExpenseTypeID ).NotEqual( 0 ).WithMessage( "ExpenseTypeID is required." );
                RuleFor( x => x.CreatedDate ).NotNull();
                RuleFor( x => x.Transaction ).SetValidator( new TransactionValidator() );
            }
        }
    
        public class TransactionBaseValidator : AbstractValidator<Transaction>
        {
            public TransactionBaseValidator()
            {
                RuleFor( x => x.BankAccountID ).NotEqual( 0 ).WithMessage( "BankAccountID is required." );
                RuleFor( x => x.EmployeeID ).NotEqual( 0 ).WithMessage( "EmployeeID is required." );
                RuleFor( x => x.TransactionDate ).NotNull();
                RuleFor( x => x.IsWithdrawal ).NotNull();
                RuleFor( x => x.Amount ).NotNull();
                RuleFor( x => x.Description ).NotEmpty();
                RuleFor( x => x.PaymentMethod ).NotEmpty();
                RuleFor( x => x.PaymentMethod ).Length( 0, 50 ).WithMessage( "PaymentMethod can not exceed 50 characters" );
            }
        }
    
        public class ExpenseValidator : ExpenseBaseValidator
        {
            public ExpenseValidator()
                    : base()
            {
                RuleFor( x => x.Transaction )
                        .NotNull()
                        .When( x => x.IsPaid )
                        .WithMessage( "An account transaction is required when the amount is paid." );
    
                RuleFor( x => x.DatePaid )
                        .NotNull()
                        .When( x => x.IsPaid )
                        .WithMessage( "Please enter the date when the expense was paid." );
            }
        }
    
        public class TransactionValidator : TransactionBaseValidator
        {
            public TransactionValidator()
                    : base() {}
        }
    
    
        public class Expense
        {
            public string Description { get; set; }
            public decimal? Amount { get; set; }
            public int BusinessID { get; set; }
            public int ExpenseTypeID { get; set; }
            public DateTime CreatedDate { get; set; }
            public Transaction Transaction { get; set; }
            public bool IsPaid { get; set; }
            public DateTime DatePaid { get; set; }
        }
    
        public class Transaction
        {
            public int BankAccountID { get; set; }
            public int EmployeeID { get; set; }
            public DateTime TransactionDate { get; set; }
            public bool? IsWithdrawal { get; set; }
            public decimal? Amount { get; set; }
            public string Description { get; set; }
            public string PaymentMethod { get; set; }
            public bool IsDeleted { get; set; }
        }
    }
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-07-05
      • 2021-07-08
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2015-12-13
      • 2014-10-22
      • 2017-03-04
      相关资源
      最近更新 更多