Reputation: 871
I have a request to one of my actions in a controller that expects an enum as a key in the Querystring. I can see that the same is set in the QueryString but an exception is thrown by the server saying the same is not set and the error:
The parameters dictionary contains a null entry for parameter 'enumVar' of non-nullable type.
is thrown.
Here are the exception details:
Exception type: System.ArgumentException
Exception message: The parameters dictionary contains a null entry for parameter 'enumVar' of non-nullable type 'NameSpace.Enums.MyEnum' for method 'System.Web.Mvc.ActionResult GetContent(Int64, NameSpace.Enums.MyEnum, System.String, Int32, Int32, Int32, Int32, Int64)' in 'NameSpace.Controllers.MyController'. An optional parameter must be a reference type, a nullable type, or be declared as an optional parameter.
Parameter name: parameters
Request path: app/My/GetContent
Let me know if you need more information. I am not sure how I should address the issue.
Update: My Enum defination:
public enum DisplayMode
{
EnumValue,
EnumValue1,
EnumValue2
}
Also I should mention that the request fails only sometimes and not always and this is not consistent. This is an error that was logged in our exception db.
Upvotes: 2
Views: 1882
Reputation: 50191
action
.MVC puts the actual controller action method name in there, no matter what you've got in your querystring or your form (assuming you are using an {action}
segment in your route). Route variables take precedence over everything, so if you happen to be trying to bind an Enum with a parameter name that's reserved, it simply ain't gonna wurk.
Upvotes: 4
Reputation:
It looks like the Default Model Binder is not dailed into enumerations. Your best bet would be to subclass the DefaultModelBinder
class and handle the scenario where a property is an enum.
public class U413ModelBinder : DefaultModelBinder
{
/// <summary>
/// Fix for the default model binder's failure to decode enum types when binding to JSON.
/// </summary>
protected override object GetPropertyValue(ControllerContext controllerContext, ModelBindingContext bindingContext,
PropertyDescriptor propertyDescriptor, IModelBinder propertyBinder)
{
var propertyType = propertyDescriptor.PropertyType;
if (propertyType.IsEnum)
{
var providerValue = bindingContext.ValueProvider.GetValue(bindingContext.ModelName);
if (null != providerValue)
{
var value = providerValue.RawValue;
if (null != value)
{
var valueType = value.GetType();
if (!valueType.IsEnum)
{
return Enum.ToObject(propertyType, value);
}
}
}
}
return base.GetPropertyValue(controllerContext, bindingContext, propertyDescriptor, propertyBinder);
}
}
Code and logic courtesy of this question.
Upvotes: 1