6

我在 ASP.Net MVC 中发现非常令人沮丧的是,默认模型绑定器Required在将空(字符串或 null)值绑定到不可为空的值类型时隐式应用注释,而不是简单地将目标保留为默认值,或者至少提供一个选项以允许它成为默认行为。

考虑到将模型上的目标属性类型更改为可空值不方便的情况,我可以使用的最短代码量是多少,以允许默认模型绑定器简单地跳过将空值绑定到不可空值的尝试值类型?我假设我需要 subclass DefaultModelBinder,但我不确定我需要重写什么来实现所需的行为。

例子:

<input type="text" name="MyField"/>

不带值提交:

public ActionResult MyAction(MyModel model)
{
    // do stuff
}

public class MyModel
{
    public int MyField { get; set; }
}

MyField应该允许该属性保留其默认值,0因为从表单中发布了一个空值。

假设我不能简单地更改属性类型 a Nullable<int>

4

1 回答 1

2

这样的事情怎么样?(免责声明:未经任何程度的置信测试)

public class NonRequiredModelBinder : DefaultModelBinder
{
    protected override object GetPropertyValue(ControllerContext controllerContext, ModelBindingContext bindingContext, PropertyDescriptor propertyDescriptor, IModelBinder propertyBinder)
    {
        var result = base.GetPropertyValue(controllerContext, bindingContext, propertyDescriptor, propertyBinder);
        if (result == null && propertyDescriptor.PropertyType.IsValueType)
            return Activator.CreateInstance(propertyDescriptor.PropertyType);

        return result;
    }
}

这个想法 - 理论上 - 是确定DefaultModelBinder分配给属性的值,检查它是否为空值,然后将其分配给ValueType正在绑定的默认值。

这应该可以防止 binder 添加ModelState错误,并且仍然不会影响其他属性的验证,例如[Range]

我建议您更进一步并创建您自己的属性(即NonRequiredAttribute)。然后在您的自定义模型绑定器中,您可以检查该属性是否具有新属性,并在它有的情况下NonRequired执行此自定义代码。

于 2012-10-11T16:31:24.610 回答