整数值模型验证

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了整数值模型验证相关的知识,希望对你有一定的参考价值。

我的模型中有一个常规的Integer(不可为空):

    [Required]
    [Range(0, Int32.MaxValue - 1)]
    public int PersonId
    {
        get;
        set;
    }

在我的qazxsw poi动作中,我接受了一个具有该属性的对象。

WebApi

现在,尽管在 public IHttpActionResult Create([FromBody] Person person) { if (!ModelState.IsValid) { return BadRequest("Some error message."); } //Do some stuff with person... } 上有一个Required属性,当一个人被发布到这个动作时,PersonId属性是ModelState.IsValid

我想这是因为true是使用默认值创建的,它是0,如果传入的JSON /查询字符串请求中没有Person字段,我想抛出一个错误。

我可以将PersonId设置为Nullable,但这没有意义。

有没有简单的方法来验证该字段是否存在且整数是否大于0? (没有针对该简单要求的自定义验证器)

答案

据我所知,设置PersonId属性对int没有任何作用。所有[Required]都确保该值不为空。您可以设置[Required]以确保添加正确的值。

如果您还没有这样做,那么为您的视图创建不同的模型并在此模型上进行数据注释可能是个好主意。我使用视图模型来确保我不会使用与整个域无关的内容污染我的“真实”模型。这样,您的PersonId只能在您的视图模型中可以为空,这是有意义的。

另一答案

[Range(1, Int32.MaxValue)]可以用来

引用这个BindRequiredAttribute关于nice blog post[Required]

它的工作方式与RequiredAttribute相同,只是它要求值来自请求 - 因此它不仅拒绝空值,还拒绝默认(或“未绑定”)值。

所以这会拒绝未绑定的整数值:

[BindRequired]
另一答案

在这种情况下,我倾向于使用[BindRequired] [Range(0, Int32.MaxValue - 1)] public int PersonId { get; set; } (nullable int),然后根据需要标记它们。然后我在整个代码中使用int?并假设它可以安全使用,因为它不会通过验证。

和@andreas说的一样,我确保在这样的时候使用“视图模型”,所以我不会将我的视图模型作为业务或数据层模型进行污染。

另一答案

实际上,对于缺少不可为空的整数参数,模型验证不起作用。 Newtonsoft.Json抛出了JSON解析异常。您可以使用以下解决方法来解析并在模型验证中包含异常。创建自定义验证属性,如下所示,并在WebApiConfig.cs中注册。

myInt.Value

//在WebApiConfig.cs中注册

public class ValidateModelAttribute : ActionFilterAttribute {
    public override void OnActionExecuting(HttpActionContext actionContext) {
        // Check if model state is valid
        if (actionContext.ModelState.IsValid == false) {
            // Return model validations object
            actionContext.Response = actionContext.Request.CreateResponse(HttpStatusCode.BadRequest,
                                                                            new ValidationResultModel(100001, actionContext.ModelState));
        }
    }

    public class ValidationError {
        public string Field { get; }

        public string Message { get; }

        public ValidationError(string field, string message) {
            Field = field != string.Empty ? field : null;
            Message = message;
        }
    }

    public class ValidationResultModel {
        public int Code { get; set; }
        public string Message { get; }
        public IDictionary<string, IEnumerable<string>> ModelState { get; private set; }

        public ValidationResultModel(int messageCode, ModelStateDictionary modelState) {
            Code = messageCode;
            Message = "Validation Failed";

            ModelState = new Dictionary<string, IEnumerable<string>>();

            foreach (var keyModelStatePair in modelState) {
                var key = string.Empty;
                key = keyModelStatePair.Key;
                var errors = keyModelStatePair.Value.Errors;
                var errorsToAdd = new List<string>();

                if (errors != null && errors.Count > 0) {
                    foreach (var error in errors) {
                        string errorMessageToAdd = error.ErrorMessage;

                        if (string.IsNullOrEmpty(error.ErrorMessage)) {
                            if (key == "model") {
                                Match match = Regex.Match(error.Exception.Message, @"'([^']*)");
                                if (match.Success)
                                    key = key + "." + match.Groups[1].Value;

                                errorMessageToAdd = error.Exception.Message;
                            } else {
                                errorMessageToAdd = error.Exception.Message;
                            }
                        }

                        errorsToAdd.Add(errorMessageToAdd);
                    }

                    ModelState.Add(key, errorsToAdd);
                }
            }
        }
    }
}

以上是关于整数值模型验证的主要内容,如果未能解决你的问题,请参考以下文章

验证 JSON 数组是不是有一个具有固定整数值的关联数组

Symfony @Assert\Type("string") 验证通过整数值

为啥 ColdFusion 认为值“7+”是一个有效的整数值,我如何验证它不是?

asp.net 验证以确保文本框具有整数值

如何为整数列的数值最大值和最小值编写数据库级验证

防止整数值在 ASP.NET Web API 模型绑定中设置布尔参数?