Câu hỏi ASP.NET MVC Một giá trị Request.Form nguy hiểm tiềm ẩn đã được phát hiện từ máy khách khi sử dụng một modelbinder tùy chỉnh


Nhận lỗi ở đây:

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

Làm cách nào để chỉ cho phép lựa chọn giá trị? I E.

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

76
2018-06-22 19:08


gốc


Có thể trùng lặp Một giá trị Request.Form nguy hiểm tiềm ẩn đã được phát hiện từ máy khách, không quan trọng nếu đó là Webforms hoặc MVC. - Erik Philips
Cảm ơn, nhưng bạn havent nhìn vào vấn đề của tôi như là khác nhau của nó - D-W
Cùng một vấn đề gốc chính xác, sự khác biệt duy nhất là có thể có MVC cách cụ thể để đối phó với nó. - Erik Philips


Các câu trả lời:


Bạn có một vài lựa chọn.

Trên mô hình, thêm thuộc tính này vào mỗi thuộc tính mà bạn cần cho phép HTML - lựa chọn tốt nhất

using System.Web.Mvc;

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

Trên hành động điều khiển, thêm thuộc tính này để cho phép tất cả HTML

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

Lực lượng vũ phu trong web.config - chắc chắn không được khuyến khích

Trong tệp web.config, trong các thẻ, chèn phần tử httpRuntime với thuộc tính requestValidationMode = "2.0". Đồng thời thêm thuộc tính validateRequest = "false" vào phần tử trang.

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

Thêm thông tin: http://davidhayden.com/blog/dave/archive/2011/01/16/AllowHtmlAttributeASPNETMVC3.aspx

Các công trình trên cho tập quán của modelbinder mặc định.

Custom ModelBinder

Có vẻ như một lời gọi đến bindingContext.ValueProvider.GetValue () trong đoạn mã trên luôn xác thực dữ liệu, bất kể thuộc tính nào. Đào vào các nguồn ASP.NET MVC cho thấy rằng DefaultModelBinder đầu tiên kiểm tra nếu yêu cầu xác nhận là bắt buộc và sau đó gọi phương thức bindingContext.UnvalidatedValueProvider.GetValue () với một tham số cho biết nếu xác nhận được yêu cầu hay không.

Rất tiếc, chúng tôi không thể sử dụng bất kỳ mã khung công tác nào vì nó được niêm phong, riêng tư hoặc bất kỳ thứ gì để bảo vệ những người không biết gì khi thực hiện các công cụ nguy hiểm, nhưng không quá khó khăn để tạo một trình tạo mô hình tùy chỉnh làm việc tôn trọng các thuộc tính AllowHtml và 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...
        }
    }
}

Phần bắt buộc khác là cách để lấy giá trị không được xác định. Trong ví dụ này, chúng ta sử dụng một phương thức mở rộng cho lớp 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);
    }
}

Thông tin thêm về điều này tại http://blogs.taiga.nl/martijn/2011/09/29/custom-model-binders-and-request-validation/


188
2018-06-23 06:03



tôi có điều này trên bộ điều khiển [HttpPost, ValidateInput (false)] và tôi vẫn nhận được lỗi - D-W
Xem câu trả lời đã sửa đổi của tôi bằng cách sử dụng mô hình tùy chỉnh - ericdc
Cảm ơn, nhưng nó không thích dòng này bindingContext.GetValueFromValueProvider - D-W
GetValueFromValueProvider cần nằm trong lớp tĩnh công cộng. Xem các chỉnh sửa ở trên. - ericdc
Ta, valueProviderResult reutrns null tho? var valueProviderResult = bindingContext.GetValueFromValueProvider (shouldPerformRequestValidation); - D-W


Thử:

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

27
2018-06-24 20:00



Khi tôi thử điều này, tôi nhận được một ngoại lệ cho biết: Thành viên không thể invocable 'System.web.HttpRequestBase.Unvalidated' không thể được sử dụng như một phương thức. Điều này có thay đổi không? - Stack0verflow
Dòng thứ hai thực sự là var re = request.Unvalidated.Form["ConfirmationMessage"]; - Stack0verflow


Mở rộng khi câu trả lời từ @ D-W, trong bộ điều khiển Chỉnh sửa của tôi, trong việc lặp qua các giá trị biểu mẫu, tôi phải thay thế tất cả các phiên bản của Request.Params.AllKeys với Request.Unvalidated.Form.AllKeys và tất cả các trường hợp Request[key] với Request.Unvalidated.Form[key].

Đây là giải pháp duy nhất có hiệu quả đối với tôi.


0
2018-02-28 17:12





Dưới đây là các bước để mã hóa ở cấp độ khách hàng và giải mã nó ở cấp độ máy chủ:

  1. Đăng biểu mẫu bằng cách sử dụng phương thức gửi jquery.

  2. Trong nút jquery nhấp vào trường mã hóa phương thức sự kiện mà bạn muốn đăng lên máy chủ. Thí dụ:

    $("#field").val(encodeURIComponent($("#field").val()))
    $("#formid").submit();
    
  3. Trong điều khiển cấp truy cập tất cả các hình thức id giá trị sử dụng

    HttpUtility.UrlDecode(Request["fieldid"])
    

Ví dụ mẫu:

  • Mức bộ điều khiển:

    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));
    }
    
  • Cấp độ khách hàng:

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

Trong chức năng Document Ready:

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

-3
2017-07-01 09:14



Công nghệ Jquery và phía máy khách không liên quan gì tới MVC, việc xác nhận hợp lệ xảy ra ở phía máy chủ với khung công tác MVC. Nó không phải là câu trả lời hợp lệ - iberodev
Cho rằng Microsoft theo nghĩa đen bỏ qua thuộc tính AllowHtml và cho rằng máy chủ giải pháp khả thi duy nhất là thay thế chức năng của trình kết nối mô hình mặc định, tôi cho rằng mã hóa phía máy khách là một tùy chọn hoàn toàn hợp lệ. - Jonathan