Reputation: 3780
I could use a custom model binder to bind a 0
and 1
to a false
and true
in this action:
[IntToBoolBinder]
public virtual ActionResult foo(bool someValue) {
}
But now suppose the argument is a strongly-typed model:
public class MyModel {
public int SomeInt { get; set; }
public string SomeString { get; set; }
public bool SomeBool { get; set; } // <-- how to custom bind this?
}
public virtual ActionResult foo(MyModel myModel) {
}
The request will contain an int
and my model expects a bool
. I could write a custom model binder for the entire MyModel
model, but I want something more generic.
Is is possible to custom bind a particular property of a strongly-typed model?
Upvotes: 1
Views: 1493
Reputation: 1651
If you want to make a custom binding to it can look like this:
public class BoolModelBinder : DefaultModelBinder
{
protected override void BindProperty(ControllerContext controllerContext, ModelBindingContext bindingContext,
PropertyDescriptor propertyDescriptor)
{
if (propertyDescriptor.PropertyType == typeof(bool))
{
Stream req = controllerContext.RequestContext.HttpContext.Request.InputStream;
req.Seek(0, SeekOrigin.Begin);
string json = new StreamReader(req).ReadToEnd();
var data = JsonConvert.DeserializeObject<Dictionary<string, string>>(json);
string value = data[propertyDescriptor.Name];
bool @bool = Convert.ToBoolean(int.Parse(value));
propertyDescriptor.SetValue(bindingContext.Model, @bool);
return;
}
else
{
base.BindProperty(controllerContext, bindingContext, propertyDescriptor);
}
}
}
But MVC and WebAPI int conversion to bool (field names must be the same) and do not need anything extra to write, so I do not know if you need the code above.
Try this demo code:
public class JsonDemo
{
public bool Bool { get; set; }
}
public class DemoController : Controller
{
[HttpPost]
public ActionResult Demo(JsonDemo demo)
{
var demoBool = demo.Bool;
return Content(demoBool.ToString());
}
}
And send JSON object :
{
"Bool" : 0
}
Upvotes: 3