ASP.NET MVC एक संभावित खतरनाक अनुरोध। कस्टम मान क्लाइंट से पता चला था जब एक कस्टम मॉडलबिंडर का उपयोग कर रहा था


95

यहाँ त्रुटि हो रही है:

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

मैं केवल मूल्यों के चयन पर कैसे अनुमति दूं? अर्थात

[ValidateInput(false)]
public object BindModel(ControllerContext controllerContext, ModelBindingContext bindingContext)
{
    ValueProviderResult value = bindingContext.ValueProvider.GetValue("ConfirmationMessage");
    ValueProviderResult value2 = bindingContext.ValueProvider.GetValue("ConfirmationMessage2");
}

1
संभावित रूप से खतरनाक रिक्वेस्ट का संभावित डुप्लिकेट.फॉर्म वैल्यू क्लाइंट से पाया गया , इससे कोई फर्क नहीं पड़ता कि वह वेबफॉर्म या एमवीसी है।
एरिक फिलिप्स

2
धन्यवाद, लेकिन आपने मेरे मुद्दे को इसके अलग
DW

एक ही सटीक रूट समस्या, एकमात्र अंतर यह है कि इससे निपटने के लिए MVC के विशिष्ट तरीके हो सकते हैं।
एरिक फिलिप्स

EF का उपयोग करते समय, देखें bizzehdee उत्तर यहां stackoverflow.com/questions/17964313/…
पेट्र

जवाबों:


223

आपके पास कुछ विकल्प हैं।

मॉडल पर इस गुण को प्रत्येक संपत्ति में जोड़ें जो आपको HTML - सर्वश्रेष्ठ विकल्प की अनुमति देने की आवश्यकता है

using System.Web.Mvc;

[AllowHtml]
public string SomeProperty { get; set; }

नियंत्रक कार्रवाई पर सभी HTML को अनुमति देने के लिए इस विशेषता को जोड़ें

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

Web.config में जानवर बल - निश्चित रूप से अनुशंसित नहीं है

Web.config फ़ाइल में, टैग के भीतर, httpRuntime तत्व को विशेषता requestValidationMode = "2.0" के साथ डालें। पृष्ठ तत्व में भी validateRequest = "false" विशेषता जोड़ें।

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

अधिक जानकारी: http://davidhayden.com/blog/dave/archive/2011/01/16/AllowHtmlAttributeASPNETMVC3.aspx

उपर्युक्त डिफ़ॉल्ट मॉडलबिंडर के उपयोग के लिए काम करता है।

कस्टम मॉडलबिंडर

ऐसा प्रतीत होता है कि ऊपर दिए कोड में बाइंडिंग कॉन्टेक्स्ट.वैल्यूप्रोइडर.जीटवैल्यू () को कॉल करने से डेटा हमेशा मान्य होता है, फिर चाहे वह किसी भी विशेषता का हो। ASP.NET MVC स्रोतों में खोदने से पता चलता है कि DefaultModelBinder पहले जाँचता है कि क्या अनुरोध सत्यापन आवश्यक है और फिर बाइंडिंग कॉन्टेक्स्ट को कॉल करें।

दुर्भाग्य से हम किसी भी फ्रेमवर्क कोड का उपयोग नहीं कर सकते क्योंकि यह सील है, निजी है या जो कुछ भी अज्ञानी देवों को खतरनाक सामान करने से बचाने के लिए है, लेकिन वर्कहॉल कस्टम मॉडल बाइंडर बनाने में बहुत मुश्किल नहीं है जो AllowHtml और ValidateInput विशेषताओं का सम्मान करता है:

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...
        }
    }
}

अन्य आवश्यक टुकड़ा एक असमान मूल्य को पुनः प्राप्त करने का एक तरीका है। इस उदाहरण में हम ModelBindingContext वर्ग के लिए एक एक्सटेंशन विधि का उपयोग करते हैं:

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);
    }
}

इस बारे में अधिक जानकारी http://blogs.taiga.nl/martijn/2011/09/29/custom-model-binders-and-request-validation/ पर


मैं नियंत्रक [HttpPost, ValidateInput (झूठा)] पर है और मैं अभी भी त्रुटि
DW

कस्टम मॉडलबाइंडर का उपयोग करते समय इसके चारों ओर मेरे संशोधित उत्तर देखें
ericdc

धन्यवाद, लेकिन यह इस लाइन बाइंडिंग को पसंद नहीं करता है। Context.GetValueFromValueProvider
DW

GetValueFromValueProvider को एक सार्वजनिक स्थैतिक वर्ग में होना चाहिए। ऊपर दिए गए संपादन देखें।
ericdc

टा, valueProviderResult फिर से null tho? var valueProviderResult = बाइंडिंग कॉन्टेक्स्ट ।GetValueFromValueProvider (shouldPerformRequestValidation);
डीडब्ल्यू

31

प्रयत्न:

HttpRequestBase request = controllerContext.HttpContext.Request;
string re = request.Unvalidated.Form.Get("ConfirmationMessage")

जब मैं यह कोशिश करता हूं, तो मुझे एक अपवाद मिलता है जो कहता है: गैर-इनवोकेबल सदस्य 'System.web.HttpRequestBase.Unvalidated' का उपयोग विधि की तरह नहीं किया जा सकता है। क्या यह बात बदल गई है?
स्टैक0वरफ्लो

7
दूसरी पंक्ति वास्तव में होनी चाहिएvar re = request.Unvalidated.Form["ConfirmationMessage"];
Stack0verflow

5

प्रपत्र मूल्यों पर पुनरावृत्ति में, मेरे संपादित नियंत्रक में @DW से जवाब पर विस्तार करते हुए,, मैं के सभी उदाहरणों को बदलने के लिए किया था Request.Params.AllKeysके साथ Request.Unvalidated.Form.AllKeysऔर के सभी उदाहरणों Request[key]के साथ Request.Unvalidated.Form[key]

यह एकमात्र समाधान था जिसने मेरे लिए काम किया।


0

के रूप में माइक गोडिन ने लिखा है, भले ही आप सेट [ValidateInput (गलत)] विशेषता, आप का उपयोग करने के Request.Unvalidated.Form बजाय Request.Form यह ASP.NET MVC 5 के साथ मेरे लिए काम किया


1
यह वास्तव में एक उपयोगी सलाह थी, जैसा कि बेस कंट्रोलर (यानी लॉग या डीबग उद्देश्यों के लिए) से डेटा एक्सेस करने के लिए किसी भी एक्सेस के लिए अनुरोध किया जाता है। मॉडल के पास यह विशेषता होने पर भी अपवाद फेंकता है।
nsimeonov

-5

ग्राहक स्तर पर सांकेतिक शब्दों में बदलना और सर्वर स्तर पर इसे डीकोड करने के चरण यहां दिए गए हैं:

  1. Jquery सबमिट करने की विधि का उपयोग करके फ़ॉर्म को पोस्ट करें।

  2. Jquery बटन में ईवेंट विधि एन्कोड फ़ील्ड पर क्लिक करें जिसे आप सर्वर पर पोस्ट करना चाहते हैं। उदाहरण:

    $("#field").val(encodeURIComponent($("#field").val()))
    $("#formid").submit();
  3. कंट्रोलर लेवल में सभी फॉर्म आईडी वैल्यू का उपयोग करके

    HttpUtility.UrlDecode(Request["fieldid"])

नमूना उदाहरण:

  • नियंत्रक स्तर:

    public ActionResult Name(string id)
    {
    
        CheckDispose();
        string start = Request["start-date"];
        string end = Request["end-date"];
        return View("Index", GetACPViewModel(HttpUtility.UrlDecode(Request["searchid"]), start, end));
    }
  • ग्राहक स्तर:

    <% using (Html.BeginForm("Name", "App", FormMethod.Post, new { id = "search-form" }))
    { %>
    <div>
    <label  for="search-text" style="vertical-align: middle" id="search-label" title="Search for an application by name, the name for who a request was made, or a BEMSID">App, (For Who) Name, or BEMSID: </label>
    <%= Html.TextBox("searchid", null, new {value=searchText, id = "search-text", placeholder = "Enter Application, Name, or BEMSID" })%>
    </div>
    <div>
    <input id="start-date" name="start-date" class="datepicker" type="text"  placeholder="Ex: 1/1/2012"/>
    </div>
    <div>
    <input id="end-date" name="end-date" class="datepicker" type="text"  placeholder="Ex: 12/31/2012"/>
    </div>
    <div>
    <input type="button" name="search" id="btnsearch" value="Search" class="searchbtn" style="height:35px"/>
    </div> 
    <% } %>

दस्तावेज़ तैयार समारोह में:

$(function () {     
  $("#btnsearch").click(function () {  
    $("#search-text").val(encodeURIComponent($("#search-text").val()));
    $("#search-form").submit();
  });
});

4
Jquery और क्लाइंट-साइड तकनीक का MVC से कोई लेना-देना नहीं है, सत्यापन MVC फ्रेमवर्क के साथ सर्वर साइड में होता है। यह एक मान्य उत्तर नहीं है
मरगोस्सवा

1
यह देखते हुए कि Microsoft शाब्दिक रूप से AllowHtml विशेषता की उपेक्षा करता है, और यह देखते हुए कि डिफ़ॉल्ट मॉडल बाइंडर की कार्यक्षमता को बदलने के लिए एकमात्र व्यावहारिक समाधान सर्वर-साइड है, मैं तर्क दूंगा कि क्लाइंट-साइड एन्कोडिंग एक पूरी तरह से वैध विकल्प है।
जोनाथन
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.