3

我有一个像这样的自定义 ValidationAttribute :


public class ReceiverRegion : ValidationAttribute
    {
        private RegionService regionService;
        private CityService cityService;

        public ReceiverRegion() : base("Incorrect region code")
        {
            this.regionService = new RegionService();
            this.cityService = new CityService();
        }

        protected override ValidationResult IsValid(object value, ValidationContext validationContext)
        {
            int regionId = Convert.ToInt32(value);
            int plate = Convert.ToInt32((validationContext.ObjectInstance as CorporateOrderItem).ReceiverCity);

            int productGroupId = Convert.ToInt32(validationContext.Items["productGroup"].ToString());

            if (!CheckReceiverRegionExistence(regionId, plate, productGroupId))
            {
                IEnumerable regions = this.regionService.GetList(cityService.GetByPlate(plate).PKCityId);

                return new CorporateOrderValidationResult(base.ErrorMessage, regions.Select(r=>r.Name));
            }
            return CorporateOrderValidationResult.Success;
        }

        private bool CheckReceiverRegionExistence(int plate, int regionId, int productGroup)
        {
            return !(regionService.GetByCityAndRegionIdForProductGroup(plate, regionId, productGroup) == null);
        }
    }

但正如您在 IsValid 方法中看到的那样,我试图返回一个继承自 ValidationResult 的自定义对象。我的问题是,我无法访问我的CorporateOrderValidationResult实例的额外成员,因为 IsValid 返回基本 ValidationResult 类型。下面是我调用 validate 并获取 ValidationResult 集合作为返回值的代码。


List results = new List();
bool isValid = Validator.TryValidateObject(instance, context, results, true);

我尝试将 results 对象转换为List<CorporateOrderValidationResult>,但无论我尝试什么(例如 -->item as CorporateOrderValidationResult或者我得到 InvalidCastExceptionresults.OfType<CorporateOrderValidationResult>()(CorporateOrderValidationResult)item)null 值。有没有可能的方法将此结果列表转换为我的自定义结果类的列表?谢谢...

4

2 回答 2

3

我试图重现这种行为,但一切都按预期工作:

public class TestClass
{
    [TestValidation]
    public string TestProp { get; set; }
}

public class TestValidationAttribute : ValidationAttribute
{
    protected override ValidationResult IsValid(object value, ValidationContext validationContext)
    {
        return new TestResult();
    }
}

public class TestResult : ValidationResult
{
    public TestResult()
        : base("test")
    {
    }
}

验证代码:

var instance = new TestClass();
var context = new ValidationContext(instance, null, null);
var results = new List<ValidationResult>();
bool isValid = Validator.TryValidateObject(instance, context, results, true);
//Contains one instance of TestResult
var customResults = results.OfType<TestResult>().ToArray();
于 2013-04-09T13:49:05.880 回答
0

我知道这是个老问题,但是当您要求自定义ValidationResult课程时,首先会出现在 Google 中。Vyacheslav Volkov 提出的示例作品,但为什么呢?

我今天花了几个小时试图让我的代码正常工作 - 关键是:

public TestResult(): base ("test")

我根本不打算使用错误消息,为此我有自己的结构,所以我这样写了我的ctor:

public TestResult() : base("")- 发送到基类的空字符串会产生后果,文档中没有提到。TryValidate()方法不会将我们的对象插入到results集合中,因为它是由我们的版本返回的IsValid(),但会为该字段构建一个带有默认错误消息的新对象,例如"Field " + fieldName + " is Invalid"并放置它而不是我们想要的那个。

于 2016-06-03T09:12:22.817 回答