I have an action that looks like
public ActionResult GetUsers(List<int> userIds) {//do stuff}
The list of userIds can become quite long, so I want to use Json.Net to deserialize it. To do so I created an IModelBinder implementation, which works fine for other objects, but never gets called for a List. The IModelBind looks like this
public class JsonBinder : System.Web.Mvc.IModelBinder
{
public object BindModel(System.Web.Mvc.ControllerContext controllerContext, System.Web.Mvc.ModelBindingContext bindingContext)
{ //Do model binding stuff using Json.Net }
}
And I register this model binder with this line
ModelBinders.Binders.Add(typeof(List<int>), new JsonBinder());
However the JsonBinder is never called. Why is this? Should I be using a ValueProvider?
Add the following event in global.asax (or add the code to your existing Application_BeginRequest handler):
protected void Application_BeginRequest()
{
foreach (var type in ModelBinders.Binders.Keys)
{
System.Diagnostics.Trace.WriteLine(
String.Format("Binder for '{0}': '{1}'",
type.ToString(),
ModelBinders.Binders[type].ToString()));
}
}
Then you can check in the VS output window what binders are currently registered. You could see something like this:
Binder for 'System.Web.HttpPostedFileBase': 'System.Web.Mvc.HttpPostedFileBaseModelBinder'
Binder for 'System.Byte[]': 'System.Web.Mvc.ByteArrayModelBinder'
Binder for 'System.Data.Linq.Binary': 'System.Web.Mvc.LinqBinaryModelBinder'
Binder for 'System.Threading.CancellationToken': 'System.Web.Mvc.CancellationTokenModelBinder'
You could also check if there is any ModelBinderProvider
that could be selecting the binder provider, because the order for selecting which model binder is used is as follows:
The attribute on the parameter of the action. See GetParameterValue method of the ControllerActionInvoker class
The Binder returned from the IModelBinderProvider. See GetBinder method in the ModelBinderDictionary class
The Binder globally registered in the ModelBinders.Binders dictionary.
The Binder defined in the [ModelBinder()]
attribute for the model type.
The DefaultModelBinder.
Use a similar approach to check the model binder providers in the BeginRequest event:
foreach (var binderprovider in ModelBinderProviders.BinderProviders)
{
System.Diagnostics.Trace.WriteLine(String.Format("Binder for '{0}'", binderprovider.ToString()));
}
Additionally, you could try to add Glimpse via nuget, as one of the tabs provides information about the model binder used for each of the parameters in the controller action.
Hopefully this will help you tracing why your model binder is not being used.
Have you tried using ModelBinder attribute in the action method?
public ActionResult GetUsers([ModelBinder(typeof(JsonBinder))] List<int> userIds)
Ref: https://msdn.microsoft.com/en-us/library/system.web.mvc.modelbinderattribute(v=vs.118).aspx
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.