Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

ASP.NET MVC A potentially dangerous Request.Form value was detected from the client when using a custom modelbinder

Getting the error here:

ValueProviderResult value = bindingContext.ValueProvider.GetValue("ConfirmationMessage"); 

How do I allow on a selection of values only? i.e.

[ValidateInput(false)] public object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext) {     ValueProviderResult value = bindingContext.ValueProvider.GetValue("ConfirmationMessage");     ValueProviderResult value2 = bindingContext.ValueProvider.GetValue("ConfirmationMessage2"); } 
like image 855
D-W Avatar asked Jun 22 '13 19:06

D-W


People also ask

How do you fix potentially dangerous request form value was detected from the client?

We can resolve your reported problem (A potentially dangerous Request. Form value was detected from the client) in ASP.NET Application. To resolve your problem, we need add the validateRequest as false in pages tag and add requestValidationMode as 2.0 in Web. config file.

What is custom model binding in mvc?

In the MVC pattern, Model binding maps the HTTP request data to the parameters of a Controllers action method. The parameter can be of a simple type like integers, strings, double etc. or they may be complex types. MVC then binds the request data to the action parameter by using the parameter name.

What is model binding?

Model binding is a simplistic way to correlate C# code with an HTTP request. The model binding applies to transforming the HTTP request data in the query's form string and form collection of the action method parameters. We can consider these parameters to be primitive type or complex type.


2 Answers

You have a few options.

On the model add this attribute to each property that you need to allow HTML - best choice

using System.Web.Mvc;  [AllowHtml] public string SomeProperty { get; set; } 

On the controller action add this attribute to allow all HTML

[ValidateInput(false)] public ActionResult SomeAction(MyViewModel myViewModel) 

Brute force in web.config - definitely not recommended

In the web.config file, within the tags, insert the httpRuntime element with the attribute requestValidationMode="2.0". Also add the validateRequest="false" attribute in the pages element.

<configuration>   <system.web>    <httpRuntime requestValidationMode="2.0" />   </system.web>   <pages validateRequest="false">   </pages> </configuration> 

More info: http://davidhayden.com/blog/dave/archive/2011/01/16/AllowHtmlAttributeASPNETMVC3.aspx

The above works for usages of the default modelbinder.

Custom ModelBinder

It appears that a call to bindingContext.ValueProvider.GetValue() in the code above always validates the data, regardless any attributes. Digging into the ASP.NET MVC sources reveals that the DefaultModelBinder first checks if request validation is required and then calls the bindingContext.UnvalidatedValueProvider.GetValue() method with a parameter that indicates if validation is required or not.

Unfortunately we can’t use any of the framework code because it’s sealed, private or whatever to protect ignorant devs from doing dangerous stuff, but it’s not too difficult to create a working custom model binder that respects the AllowHtml and ValidateInput attributes:

public class MyModelBinder: IModelBinder {     public object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)     {         // First check if request validation is required         var shouldPerformRequestValidation = controllerContext.Controller.ValidateRequest && bindingContext.ModelMetadata.RequestValidationEnabled;          // Get value         var valueProviderResult = bindingContext.GetValueFromValueProvider(shouldPerformRequestValidation);         if (valueProviderResult != null)         {             var theValue = valueProviderResult.AttemptedValue;              // etc...         }     } } 

The other required piece is a way to retrieve an unvalidated value. In this example we use an extension method for the ModelBindingContext class:

public static class ExtensionHelpers {     public static ValueProviderResult GetValueFromValueProvider(this ModelBindingContext bindingContext, bool performRequestValidation)     {         var unvalidatedValueProvider = bindingContext.ValueProvider as IUnvalidatedValueProvider;         return (unvalidatedValueProvider != null)           ? unvalidatedValueProvider.GetValue(bindingContext.ModelName, !performRequestValidation)           : bindingContext.ValueProvider.GetValue(bindingContext.ModelName);     } } 

More info on this at http://blogs.taiga.nl/martijn/2011/09/29/custom-model-binders-and-request-validation/

like image 93
ericdc Avatar answered Sep 19 '22 11:09

ericdc


Try:

HttpRequestBase request = controllerContext.HttpContext.Request; string re = request.Unvalidated.Form.Get("ConfirmationMessage") 
like image 45
D-W Avatar answered Sep 20 '22 11:09

D-W