1

我有一个实现接口 IValidatable 的 IEntity 接口

public interface IValidatable {
    bool IsValid { get; }
    bool IsValidForPersistence { get; }
    // Rules applied at UI time (please enter your name, etc)
    IEnumerable<RuleViolation> GetRuleViolations();
    // Rules to be applied only at persistence time
    IEnumerable<RuleViolation> GetPersistenceRuleViolations();
}

public interface IEntity : IValidatable {
    int ID { get; set; }
}

并且为了方便起见,我已经实现了我的 Entity 类,例如:

 public abstract class Entity : IEntity {

        public virtual int ID { get; set; }

        public virtual bool IsValid {
            get { return RuleViolations().Count() == 0; }
        }

        public virtual bool IsValidForPersistence {
            get { return PersistenceRuleViolations().Count() == 0; }
        }

        public virtual IEnumerable<RuleViolation> GetRuleViolations() {
            return new List<RuleViolation>();
        }

        public virtual IEnumerable<RuleViolation> GetPersistenceRuleViolations() {
            return new List<RuleViolation>();
        }
    }

默认情况下,实体是有效的,直到 GetRuleViolations() 或 GetPersistenceRuleViolations() 被覆盖。

  public partial class Company {

      public override IEnumerable<RuleViolation> GetRuleViolations() {
         if (String.IsNullOrEmpty(CompanyName))
                yield return new RuleViolation("CompanyName", "Name is required.");
     }

      public override IEnumerable<RuleViolation> GetPersistenceRuleViolations() {
         // Include standard rules too
         foreach (RuleViolation rule in RuleViolations) {
              yield return rule;
          }
        // Check some data based on a referenced entity "Bid"
        if (!Active && Bid.Active)
            yield return new RuleViolation("Active", 
               "When Active is set to false, the Bid must also be inactive.");
     }
  }

我知道这对于验证来说有点幼稚,所以除了任何错别字之外,还有什么可以改进的?

4

3 回答 3

1

我建议查看具有良好业务规则和验证基础框架的 NCommon 框架,或者也支持来自同一规则集的客户端验证的 xVal 验证框架。

于 2009-10-07T22:31:26.017 回答
1

请记住,如果您从另一个实体派生出一个实体,例如。来自 Person 的客户,您需要一个 foeach 来获取基类违规:

  public override IEnumerable<RuleViolation> GetRuleViolations() 
  {
     // inherit base class valiations
     foreach (var violation in base.GetRuleViolations())
     {
         yield return violation;
     }

     // add own validations
     if (String.IsNullOrEmpty(CompanyName))
         yield return new RuleViolation("CompanyName", "Name is required.");
  }

这不是很好。

就个人而言,我也会寻找现有的东西,因为验证是一个普遍的问题,并且已经有很多解决方案。

于 2009-10-08T00:54:51.490 回答
0

我正在使用 ASP.NET MVC 并使用 Data Annotation Validators 做类似的事情。然而,我继承ValidationAttribute并覆盖FormatErrorMessage,以便我可以集体返回错误。

于 2009-10-07T22:35:29.947 回答