Od klienta wykryto potencjalnie niebezpieczną wartość Request.Form


1471

Za każdym razem, gdy użytkownik publikuje coś w mojej aplikacji internetowej <lub >na stronie, pojawia się ten wyjątek.

Nie chcę wchodzić w dyskusję na temat mądrości zgłaszania wyjątku lub zawieszania całej aplikacji internetowej, ponieważ ktoś wpisał znak w polu tekstowym, ale szukam eleganckiego sposobu, aby sobie z tym poradzić.

Przechwytywanie wyjątku i wyświetlanie

Wystąpił błąd, wróć i ponownie wpisz cały formularz, ale tym razem nie używaj <

nie wydaje mi się wystarczająco profesjonalny.

Wyłączenie post validation ( validateRequest="false") z pewnością pozwoli uniknąć tego błędu, ale pozostawi stronę podatną na wiele ataków.

Idealnie: gdy wystąpi zwrotny zwrot zawierający znaki HTML, ta zaksięgowana wartość w kolekcji Form zostanie automatycznie zakodowana w HTML. Tak więc .Textwłaściwość mojego pola tekstowego będziesomething & lt; html & gt;

Czy mogę to zrobić w programie obsługi?


68
Pamiętaj, że możesz otrzymać ten błąd, jeśli w danych wejściowych masz również nazwy encji HTML (& amp;) lub numery encji (& # 39;).
Drew Noakes,

18
Cóż, ponieważ to moje pytanie, wydaje mi się, że mogę zdefiniować, o co właściwie chodzi: zawieszenie całego procesu aplikacji i zwrócenie ogólnego komunikatu o błędzie, ponieważ ktoś wpisał „<”, to przesada. Zwłaszcza, że ​​wiesz, że większość ludzi po prostu „validateRequest = false”, aby się go pozbyć, tym samym ponownie otwierając lukę
Radu094,

7
@DrewNoakes: nazwy jednostek (& amp;) nie wydają się stanowić problemu według moich testów (testowanych w .Net 4.0), chociaż numery jednostek (& # 39;) nie sprawdzają poprawności (jak powiedziałeś). Jeśli zdemontujesz metodę System.Web.CrossSiteScriptingValidation.IsDangerousString za pomocą .Net Reflector, zobaczysz, że kod szuka specjalnie tagów HTML (zaczynających się na <) i numerów encji (zaczynających się na & #)
Gyum Fox

5
Utwórz nową witrynę w VS2014 przy użyciu domyślnego projektu MVC i uruchom ją. Kliknij link rejestracji, dodaj dowolny e-mail i użyj „<P455-0r [!” jako hasło. Ten sam błąd po wyjęciu z pudełka, nie próbując zrobić niczego złośliwego, pole hasła nie będzie wyświetlane, więc nie będzie to atak XSS, ale jedynym sposobem na jego naprawienie jest całkowite usunięcie sprawdzania poprawności za pomocą ValidateInput (false) ? Sugestia AllowHtml nie działa w tej sytuacji, nadal wysadziła się z tym samym błędem. Od klienta wykryto potencjalnie niebezpieczną wartość Request.Form (hasło = „<P455-0r [!”).
stephenbayer

TL; DR wstawiono <httpRuntime requestValidationMode="2.0" />do web.config

Odpowiedzi:


1080

Myślę, że atakujesz go pod niewłaściwym kątem, próbując zakodować wszystkie opublikowane dane.

Pamiętaj, że „ <” może również pochodzić z innych zewnętrznych źródeł, takich jak pole bazy danych, konfiguracja, plik, kanał i tak dalej.

Ponadto „ <” nie jest z natury niebezpieczne. Jest to niebezpieczne tylko w określonym kontekście: podczas pisania ciągów, które nie zostały zakodowane na wyjściu HTML (z powodu XSS).

W innych kontekstach różne podciągi są niebezpieczne, na przykład, jeśli wpiszesz podany przez użytkownika adres URL w podlinkowaniu, podciąg „ javascript:” może być niebezpieczny. Z drugiej strony pojedynczy znak cudzysłowu jest niebezpieczny podczas interpolacji ciągów w zapytaniach SQL, ale jest całkowicie bezpieczny, jeśli jest częścią nazwy przesłanej z formularza lub odczytanej z pola bazy danych.

Najważniejsze jest to: nie można filtrować losowych danych wejściowych pod kątem niebezpiecznych znaków, ponieważ każda postać może być niebezpieczna w odpowiednich okolicznościach. Powinieneś zakodować w miejscu, w którym niektóre określone znaki mogą stać się niebezpieczne, ponieważ przechodzą na inny podjęzyk, w którym mają specjalne znaczenie. Kiedy piszesz ciąg znaków do HTML, powinieneś zakodować znaki, które mają specjalne znaczenie w HTML, używając Server.HtmlEncode. Jeśli przekażesz ciąg do dynamicznej instrukcji SQL, powinieneś zakodować różne znaki (lub lepiej, pozwól, aby środowisko to zrobiło za Ciebie, używając przygotowanych instrukcji itp.).

Gdy masz pewność, że kodujesz HTML wszędzie, gdzie przekazujesz ciągi znaków do HTML, ustaw validateRequest="false"w <%@ Page ... %>dyrektywie .aspxplik (i).

W .NET 4 może być konieczne zrobienie czegoś więcej. Czasami konieczne jest również dodanie <httpRuntime requestValidationMode="2.0" />do pliku web.config ( odniesienie ).


74
Do tych, którzy przyjdą późno: validateRequest = "false" trafia do dyrektywy strony (pierwszy wiersz pliku .aspx)
MGOwen,

56
Wskazówka: wstaw <httpRuntime requestValidationMode="2.0" />tag lokalizacji, aby uniknąć zabicia użytecznej ochrony zapewnianej przez sprawdzanie poprawności z reszty witryny.
Brian

297
W MVC3 jest [AllowHtml]to właściwość modelu.
Jeremy Holovacs,

2
Aby je wyłączyć globalnie dla MVC 3 trzeba także GlobalFilters.Filters.Add(new ValidateInputAttribute(false));w Application_Start().
Alex

15
@MGOwen można również dodać dyrektywy page do web.config przez <pages validateRequest="false" />w <system.web />. Spowoduje to zastosowanie tej właściwości do wszystkich stron.
oliver-clare

504

Istnieje inne rozwiązanie tego błędu, jeśli używasz ASP.NET MVC:

Próbka C #:

[HttpPost, ValidateInput(false)]
public ActionResult Edit(FormCollection collection)
{
    // ...
}

Próbka Visual Basic:

<AcceptVerbs(HttpVerbs.Post), ValidateInput(False)> _
Function Edit(ByVal collection As FormCollection) As ActionResult
    ...
End Function

problem może pojawić się, gdy trzeba na jednej stronie całej aplikacji

3
Możesz także dodać atrybut [ValidateInput (false)] na poziomie klasy. Dodanie go do podstawowej klasy kontrolera będzie miało zastosowanie do wszystkich akcji metody kontrolera.
Shan Plourde

@Zack Dzięki za rozwiązanie. Z drugiej strony zastanawiam się, czy [AllowHtml]jest lepsze niż ValidateInput(false), ponieważ [AllowHtml]jest definiowane od razu dla właściwości, tj. Pola Edytora i za każdym razem, gdy jest używana, nie trzeba jej używać do kilku działań. Co sugerujesz?
Jack

@Zack Peterson Czy korzystanie z niego jest bezpieczne? Brak problemu z bezpieczeństwem?
shrey Pav

416

W ASP.NET MVC (od wersji 3) możesz dodać AllowHtmlatrybut do właściwości w swoim modelu.

Pozwala żądaniu uwzględnić znaczniki HTML podczas wiązania modelu, pomijając sprawdzanie poprawności żądania dla właściwości.

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

12
O wiele lepiej robić to deklaratywnie niż w kontrolerze!
Andiih,

29
Jedyna poprawna odpowiedź! wyłączenie sprawdzania poprawności działania kontrolera jest zhackowane. Aby wyłączyć sprawdzanie poprawności na poziomie aplikacji, deweloperzy muszą zostać powieszeni!
trailmax

Czy to zniknęło w MVC 4?
granadaCoder

1
Jaka jest różnica między ValidateInput(false)i AllowHtml? Jaka jest przewaga jednego nad drugim? Kiedy chciałbym użyć AllowHtmlzamiast ValidateInput(false)? Kiedy chcę użyć ValidateInput(false)w ciągu AllowHtml? Kiedy chciałbym korzystać z obu? Czy warto używać obu?
Ian Boyd

3
ValidateInput jest w metodzie, AllowHtml jest we właściwości modelu - więc zezwalasz tylko na tę, której spodziewasz się mieć html - nie wszystkie
Anthony Johnston

213

Jeśli korzystasz z .NET 4.0, upewnij się, że dodajesz to do pliku web.config wewnątrz <system.web>tagów:

<httpRuntime requestValidationMode="2.0" />

W .NET 2.0 sprawdzanie poprawności aspxżądań dotyczyło tylko żądań. W .NET 4.0 został on rozszerzony o wszystkie żądania. Możesz przywrócić sprawdzanie poprawności XSS tylko podczas przetwarzania .aspx, określając:

requestValidationMode="2.0"

Możesz całkowicie wyłączyć sprawdzanie poprawności , określając:

validateRequest="false"

30
Wewnątrz <system.web>tagów.
Hosam Aly,

8
Umieściłem to w pliku web.config, ale wciąż pojawia się błąd „Potencjalnie niebezpieczna wartość Request.Form”
Filip

20
Wygląda na to, że <httpRuntime requestValidationMode = "2.0" /> działa tylko wtedy, gdy na komputerze jest zainstalowane środowisko 2.0. Co się stanie, jeśli środowisko 2.0 nie zostanie wcale zainstalowane, ale tylko środowisko 4.0 zostanie zainstalowane?
Samuel

To całkowicie zadziałało dla mnie. Żaden dokument kroków z pozostałych odpowiedzi nie był konieczny (w tym validateRequest = "false")!
tom redfern

112

W przypadku ASP.NET 4.0 można zezwolić na znaczniki jako dane wejściowe dla konkretnych stron zamiast dla całej witryny, umieszczając je w jednym <location>elemencie. Dzięki temu wszystkie Twoje strony będą bezpieczne. NIE musisz umieszczać ValidateRequest="false"strony .aspx.

<configuration>
...
  <location path="MyFolder/.aspx">
    <system.web>
      <pages validateRequest="false" />
      <httpRuntime requestValidationMode="2.0" />
    </system.web>
  </location>
...
</configuration>

Bezpieczniej jest to kontrolować w pliku web.config, ponieważ na poziomie witryny można zobaczyć, które strony zezwalają na znaczniki jako dane wejściowe.

Nadal musisz programowo sprawdzić poprawność danych wejściowych na stronach, na których sprawdzanie poprawności żądania jest wyłączone.


Więcej informacji na żądanie ValidationMode = 2 | 4 tutaj: msdn.microsoft.com/en-us/library/…
GlennG

Niestety nie będzie to działać z ASP.net 2.0 w obecnej postaci. Usuń wiersz httpRuntime i będzie działać.
Fandango68,

Dodałem ostrzeżenie przypominające ludziom o ręcznym sprawdzaniu poprawności danych wejściowych, gdy sprawdzanie poprawności jest wyłączone.
Carter Medlin,

72

Poprzednie odpowiedzi są świetne, ale nikt nie powiedział, jak wykluczyć jedno pole z weryfikacji pod kątem wstrzyknięć HTML / JavaScript. Nie wiem o poprzednich wersjach, ale w MVC3 Beta możesz to zrobić:

[HttpPost, ValidateInput(true, Exclude = "YourFieldName")]
public virtual ActionResult Edit(int id, FormCollection collection)
{
    ...
}

To nadal sprawdza poprawność wszystkich pól z wyjątkiem jednego wykluczonego. Zaletą tego jest to, że twoje atrybuty sprawdzania poprawności nadal sprawdzają poprawność pola, ale po prostu nie otrzymujesz wyjątków „Potencjalnie niebezpieczne żądanie. Wykryto formularz od klienta”.

Użyłem tego do sprawdzania poprawności wyrażenia regularnego. Zrobiłem własny atrybut ValidationAttribute, aby sprawdzić, czy wyrażenie regularne jest prawidłowe, czy nie. Ponieważ wyrażenia regularne mogą zawierać coś, co wygląda jak skrypt, zastosowałem powyższy kod - wyrażenie regularne jest nadal sprawdzane, czy jest poprawne, czy nie, ale nie, jeśli zawiera skrypty lub HTML.


10
Niestety wygląda na to, że funkcja wykluczania została usunięta z MVC 3 RTW :(
Matt Greer

2
Nie został również uwzględniony w MVC 4
wilsjd

9
Użyj [AllowHtml]właściwości modelu zamiast [ValidateInput]akcji, aby osiągnąć ten sam efekt końcowy.
Mrchief

2
@Christof Pamiętaj, że moja odpowiedź ma 5 lat. Od dłuższego czasu nie spotkałem się z tym problemem, więc mogą istnieć o wiele lepsze sposoby radzenia sobie z nim. Jeśli chodzi o te dwie opcje, myślę, że zależy to od twojej sytuacji. Być może ujawniasz ten model w więcej niż jednej akcji, aw niektórych miejscach HTML jest dozwolony lub nie. W takim przypadku [AllowHtml]nie ma opcji. Polecam sprawdzenie tego artykułu: weblogs.asp.net/imranbaloch/... , ale on też jest nieco stary i może być nieaktualny.
gligoran

1
Wciąż istnieje sposób na wykluczenie określonych parametrów metody z walidacji, sprawdź moją odpowiedź tutaj: stackoverflow.com/a/50796666/56621
Alex

51

W ASP.NET MVC należy ustawić requestValidationMode = "2.0" i validateRequest = "false" w pliku web.config i zastosować atrybut ValidateInput do akcji kontrolera:

<httpRuntime requestValidationMode="2.0"/>

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

i

[Post, ValidateInput(false)]
public ActionResult Edit(string message) {
    ...
}

2
Dla mnie validateRequest="false"nie było to konieczne, tylkorequestValidationMode="2.0"
tom redfern

requestValidationMode = "2.0" nadal generuje błąd z danymi zakodowanymi w HTML. Żadne rozwiązanie oprócz base64 wszystko koduje, a następnie przesyła.
MC9000,

48

Możesz kodować zawartość HTML w polu tekstowym, ale niestety nie powstrzyma to wyjątku. Z mojego doświadczenia wynika, że ​​nie ma takiej możliwości i musisz wyłączyć sprawdzanie poprawności strony. Robiąc to, mówisz: „Będę ostrożny, obiecuję”.


43

W przypadku MVC zignoruj ​​sprawdzanie poprawności danych wejściowych przez dodanie

[ValidateInput (false)]

powyżej każdej akcji w kontrolerze.


Wydaje się, że nie działa to w przypadku przejścia do metody kontrolera skonfigurowaną trasą.
PandaWood

W rzeczywistości wyjaśnienie techniczne polega na tym, że działa to tylko wtedy, gdy obrażający znak znajduje się w „ciągu zapytania” ... jeśli znajduje się na ścieżce żądania, atrybut walidacji nie działa
PandaWood

42

Możesz złapać ten błąd w Global.asax. Nadal chcę sprawdzić poprawność, ale pokażę odpowiedni komunikat. Na blogu wymienionym poniżej dostępna była taka próbka.

    void Application_Error(object sender, EventArgs e)
    {
        Exception ex = Server.GetLastError();

        if (ex is HttpRequestValidationException)
        {
            Response.Clear();
            Response.StatusCode = 200;
            Response.Write(@"[html]");
            Response.End();
        }
    }

Przekierowanie na inną stronę również wydaje się rozsądną odpowiedzią na wyjątek.

http://www.romsteady.net/blog/2007/06/how-to-catch-httprequestvalidationexcep.html


40

Odpowiedź na to pytanie jest prosta:

var varname = Request.Unvalidated["parameter_name"];

Spowoduje to wyłączenie sprawdzania poprawności dla konkretnego żądania.


1
Dotyczy tylko ASP.NET 4.5 (i prawdopodobnie wszystkiego, co nastąpi po nim). Wersja 4.5 nie obsługuje tego.
Beska

3
Chciałbym móc podskoczyć w ten sposób. Używam .NET 4.5 i właśnie tego potrzebowałem, ponieważ nie używam MVC i nie mogę zmienić pliku web.config.
Chris Gillum,

1
Tak, ale co, jeśli używasz .Net 2? Niektórzy z nas nie mają wyboru
Fandango68,

to dostaje parametry POST lub GET?
max4ever 15.0415

Czy mówisz, że zapobiega to zgłoszonemu wyjątkowi? A może .net 4.5 opóźnia wyjątek i sprawdzanie poprawności, dopóki dane nie zostaną odczytane z Request?
ebyrob,

34

Należy pamiętać, że niektóre kontrolki .NET automatycznie kodują dane wyjściowe w formacie HTML. Na przykład ustawienie właściwości .Text w kontrolce TextBox spowoduje jej automatyczne zakodowanie. Oznacza to w szczególności konwersję <na &lt;, >na &gt;i &na &amp;. Uważaj więc na to ...

myTextBox.Text = Server.HtmlEncode(myStringFromDatabase); // Pseudo code

Jednak właściwość .Text dla HyperLink, Literal i Label nie koduje HTML, więc otacza Server.HtmlEncode (); wszystko, co jest ustawione w tych właściwościach, jest koniecznością, jeśli chcesz zapobiec <script> window.location = "http://www.google.com"; </script>wyświetlaniu ich na stronie, a następnie wykonywaniu.

Wykonaj małe eksperymenty, aby zobaczyć, co zostanie zakodowane, a co nie.


29

W pliku web.config w tagach wstaw element httpRuntime z atrybutem requestValidationMode = „2.0”. Dodaj także atrybut validateRequest = "false" w elemencie Pages.

Przykład:

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

1
Dla mnie, validateRequest = "false" nie było konieczne, tylko requestValidationMode = "2.0"
tom redfern

3
Sekcja „strony” musi znajdować się w sekcji „system.web”.
Carter Medlin

niebezpieczna odpowiedź, jeszcze raz.
MC9000,

Potrzebowałem obu. Dzięki
Jack

23

Jeśli nie chcesz wyłączać ValidateRequest, musisz zaimplementować funkcję JavaScript, aby uniknąć wyjątku. To nie jest najlepsza opcja, ale działa.

function AlphanumericValidation(evt)
{
    var charCode = (evt.charCode) ? evt.charCode : ((evt.keyCode) ? evt.keyCode :
        ((evt.which) ? evt.which : 0));

    // User type Enter key
    if (charCode == 13)
    {
        // Do something, set controls focus or do anything
        return false;
    }

    // User can not type non alphanumeric characters
    if ( (charCode <  48)                     ||
         (charCode > 122)                     ||
         ((charCode > 57) && (charCode < 65)) ||
         ((charCode > 90) && (charCode < 97))
       )
    {
        // Show a message or do something
        return false;
    }
}

Następnie w kodzie z tyłu, w zdarzeniu PageLoad, dodaj atrybut do kontrolki za pomocą następnego kodu:

Me.TextBox1.Attributes.Add("OnKeyPress", "return AlphanumericValidation(event);")

4
To nadal pozostawia aplikację podatną na złożone żądania POST. Zwykły użytkownik będzie miał problemy z wprowadzaniem znaków takich jak:: lub cudzysłowy, ale zwykły haker nie będzie miał problemów z wysyłaniem źle sformatowanych danych na serwer. Opuściłbym to waaayay w dół.
Radu094,

13
@ Radu094: To rozwiązanie pozwala zachować wartość ValidateRequest = true, co oznacza, że ​​hakerzy nadal uderzą w tę ścianę. Głosuj w górę, ponieważ pozostawia to Cię mniej podatnym na zagrożenia niż wyłączenie ValidateRequest.
jbehren

21

Wygląda na to, że nikt jeszcze nie wspomniał o tym poniżej, ale rozwiązuje to problem. I zanim ktokolwiek powie: tak, to Visual Basic ... fuj.

<%@ Page Language="vb" AutoEventWireup="false" CodeBehind="Example.aspx.vb" Inherits="Example.Example" **ValidateRequest="false"** %>

Nie wiem, czy są jakieś wady, ale dla mnie zadziałało to niesamowicie.


Działa dla formularzy internetowych c # lub VB
TheAlbear

19

Innym rozwiązaniem jest:

protected void Application_Start()
{
    ...
    RequestValidator.Current = new MyRequestValidator();
}

public class MyRequestValidator: RequestValidator
{
    protected override bool IsValidRequestString(HttpContext context, string value, RequestValidationSource requestValidationSource, string collectionKey, out int validationFailureIndex)
    {
        bool result = base.IsValidRequestString(context, value, requestValidationSource, collectionKey, out validationFailureIndex);

        if (!result)
        {
            // Write your validation here
            if (requestValidationSource == RequestValidationSource.Form ||
                requestValidationSource == RequestValidationSource.QueryString)

                return true; // Suppress error message
        }
        return result;
    }
}

Miły! Nie wiedział o możliwości zastąpienia narzędzia sprawdzania poprawności. Zamiast po prostu powiedzieć „ok”, tak jak ty, rozszerzyłem ten pomysł, aby nie sprawdzać poprawności pól zakończonych na „_NoValidation” jako ich nazwa. Kod poniżej.
Walden Leverich

Walden Leverich, aby to zrobić, zobacz [AllowHtml] Attribure
Sel

Sel, tak w środowisku MVC, które działałoby. Ale w aplikacji do tworzenia formularzy internetowych nie mam na to modelu. :-)
Walden Leverich

15

Jeśli używasz frameworka 4.0, to wpis w pliku web.config (<pages validateRequest = "false" />)

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

Jeśli używasz frameworka 4.5, to wpis w pliku web.config (requestValidationMode = "2.0")

<system.web>
    <compilation debug="true" targetFramework="4.5" />
    <httpRuntime targetFramework="4.5" requestValidationMode="2.0"/>
</system.web>

Jeśli chcesz tylko dla jednej strony, w pliku aspx powinieneś umieścić pierwszy wiersz w następujący sposób:

<%@ Page EnableEventValidation="false" %>

jeśli masz już coś w rodzaju <% @ Page, po prostu dodaj resztę => EnableEventValidation="false"%>

Polecam tego nie robić.


13

W ASP.NET możesz złapać wyjątek i coś z tym zrobić, na przykład wyświetlić przyjazną wiadomość lub przekierować na inną stronę ... Istnieje również możliwość samodzielnej obsługi sprawdzania poprawności ...

Wyświetl przyjazną wiadomość:

protected override void OnError(EventArgs e)
{
    base.OnError(e);
    var ex = Server.GetLastError().GetBaseException();
    if (ex is System.Web.HttpRequestValidationException)
    {
        Response.Clear();
        Response.Write("Invalid characters."); //  Response.Write(HttpUtility.HtmlEncode(ex.Message));
        Response.StatusCode = 200;
        Response.End();
    }
}

13

Myślę, że możesz to zrobić w module; ale to pozostawia otwarte pytania; co jeśli chcesz zapisać dane wejściowe w bazie danych? Nagle, ponieważ zapisujesz zakodowane dane w bazie danych, w końcu ufasz wejściom, co jest prawdopodobnie złym pomysłem. Idealnie przechowujesz nieprzetworzone nieprzetworzone dane w bazie danych i kodowaniu za każdym razem.

Lepszym rozwiązaniem jest wyłączenie ochrony na poziomie strony, a następnie kodowanie za każdym razem.

Zamiast korzystać z Server.HtmlEncode powinieneś przyjrzeć się nowszej, bardziej kompletnej bibliotece Anti-XSS od zespołu Microsoft ACE.


12

Przyczyna

Program ASP.NET domyślnie sprawdza poprawność wszystkich formantów wejściowych pod kątem potencjalnie niebezpiecznych treści, które mogą prowadzić do skryptów krzyżowych (XSS) i wstrzyknięć SQL . W związku z tym nie zezwala na taką treść, zgłaszając powyższy wyjątek. Domyślnie zaleca się zezwalanie na to sprawdzanie przy każdym opóźnieniu zwrotnym.

Rozwiązanie

W wielu przypadkach musisz przesłać treść HTML na swoją stronę za pomocą Rich TextBoxes lub Rich Text Editor. W takim przypadku możesz uniknąć tego wyjątku, ustawiając tag ValidateRequest w @Pagedyrektywie na false.

<%@ Page Language="C#" AutoEventWireup="true" ValidateRequest = "false" %>

Spowoduje to wyłączenie sprawdzania poprawności żądań dla strony, dla której ustawiono flagę ValidateRequest na false. Jeśli chcesz to wyłączyć, sprawdź w swojej aplikacji internetowej; musisz ustawić wartość false w swojej sekcji web.config <system.web>

<pages validateRequest ="false" />

W przypadku platform .NET 4.0 lub nowszych należy również dodać następujący wiersz w sekcji <system.web>, aby powyższe działało.

<httpRuntime requestValidationMode = "2.0" />

Otóż ​​to. Mam nadzieję, że pomoże to w pozbyciu się powyższego problemu.

Odniesienie do: Błąd ASP.Net: Wykryto potencjalnie niebezpieczną wartość Request.Form od klienta


10

Znalazłem rozwiązanie, które wykorzystuje JavaScript do kodowania danych, które są dekodowane w .NET (i nie wymaga jQuery).

  • Ustaw pole tekstowe jako element HTML (jak textarea) zamiast ASP.
  • Dodaj ukryte pole.
  • Dodaj następującą funkcję JavaScript do nagłówka.

    funkcja boo () {targetText = document.getElementById ("HiddenField1"); sourceText = document.getElementById („skrzynka użytkownika”); targetText.value = escape (sourceText.innerText); }

W swoim obszarze tekstowym umieść onchange, który wywołuje boo ():

<textarea id="userbox"  onchange="boo();"></textarea>

Wreszcie, w .NET, użyj

string val = Server.UrlDecode(HiddenField1.Value);

Wiem, że jest to jednokierunkowe - jeśli potrzebujesz dwukierunkowego, musisz wykazać się kreatywnością, ale zapewnia to rozwiązanie, jeśli nie możesz edytować pliku web.config

Oto przykład, który I (MC9000) wymyśliłem i używam przez jQuery:

$(document).ready(function () {

    $("#txtHTML").change(function () {
        var currentText = $("#txtHTML").text();
        currentText = escape(currentText); // Escapes the HTML including quotations, etc
        $("#hidHTML").val(currentText); // Set the hidden field
    });

    // Intercept the postback
    $("#btnMyPostbackButton").click(function () {
        $("#txtHTML").val(""); // Clear the textarea before POSTing
                               // If you don't clear it, it will give you
                               // the error due to the HTML in the textarea.
        return true; // Post back
    });


});

I znaczniki:

<asp:HiddenField ID="hidHTML" runat="server" />
<textarea id="txtHTML"></textarea>
<asp:Button ID="btnMyPostbackButton" runat="server" Text="Post Form" />

To działa świetnie. Jeśli haker spróbuje opublikować, omijając JavaScript, zobaczy tylko błąd. Możesz również zapisać wszystkie dane zakodowane w bazie danych, a następnie usunąć z niego krajobraz (po stronie serwera) oraz przeanalizować i sprawdzić ataki przed wyświetleniem w innym miejscu.


To dobre rozwiązanie. Jest to właściwy ręczny sposób na samodzielne kontrolowanie go i nie unieważnianie całej witryny lub strony
Fandango68,

Upewnij się, że używasz znaczników HTML, a nie kontrolki ASP.Net (tj. No runat = "server") dla obszaru tekstowego, a następnie użyj ukrytego kontrolki ASP.Net dla ukrytego. To najlepsze rozwiązanie, jakie widziałem bez kompromisów. Oczywiście chcesz przeanalizować swoje dane pod kątem XSS, SQL Injection po stronie serwera, ale przynajmniej możesz opublikować HTML
MC9000

escape(...)może zająć dużo czasu. W moim przypadku znacznikiem był cały plik XML (2 MB). Możesz zapytać: „Dlaczego po prostu nie użyjesz <input type="file"...i ... Zgadzam się z tobą :)
The Red Pea

10

Inne rozwiązania tutaj są fajne, jednak to trochę królewski ból z tyłu, gdy trzeba zastosować [AllowHtml] do każdej pojedynczej właściwości Modelu, szczególnie jeśli masz ponad 100 modeli na przyzwoitej stronie.

Jeśli tak jak ja, chcesz wyłączyć tę funkcję (całkiem bezcelową) z całej witryny, możesz zastąpić metodę Execute () w kontrolerze podstawowym (jeśli nie masz jeszcze kontrolera podstawowego, sugeruję, aby go utworzyć, mogą być całkiem przydatne do stosowania wspólnej funkcjonalności).

    protected override void Execute(RequestContext requestContext)
    {
        // Disable requestion validation (security) across the whole site
        ValidateRequest = false;
        base.Execute(requestContext);
    }

Tylko upewnij się, że kodujesz HTML wszystko, co jest wypompowywane do widoków pochodzących z danych wejściowych użytkownika (tak czy inaczej jest to domyślne zachowanie w ASP.NET MVC 3 z Razor, więc chyba że z jakiegoś dziwnego powodu używasz Html.Raw () nie powinien wymagać tej funkcji.


9

Wystąpił również ten błąd.

W moim przypadku użytkownik wprowadził znak akcentowany áw nazwie roli (w odniesieniu do dostawcy członkostwa ASP.NET).

Przekazuję nazwę roli do metody, aby przyznać użytkownikom tę rolę, a $.ajaxżądanie wysłania nie powiodło się ...

Zrobiłem to, aby rozwiązać problem:

Zamiast

data: { roleName: '@Model.RoleName', users: users }

Zrób to

data: { roleName: '@Html.Raw(@Model.RoleName)', users: users }

@Html.Raw wykonał lewę.

Otrzymałem nazwę roli jako wartość HTML roleName="Cadastro b&#225;s". Ta wartość z jednostką HTML &#225;była blokowana przez ASP.NET MVC. Teraz otrzymuję roleNamewartość parametru taką, jaka powinna być: roleName="Cadastro Básico"a silnik ASP.NET MVC nie będzie już blokował żądania.


9

Wyłączyć sprawdzanie strony, jeśli naprawdę potrzebujesz znaków specjalnych, takich jak, >,, <, itd. Następnie upewnić się, że gdy wyświetlana jest wprowadzane przez użytkownika dane są kodowane w formacie HTML.

Podczas sprawdzania poprawności strony występuje luka w zabezpieczeniach, więc można ją obejść. Nie należy polegać wyłącznie na sprawdzaniu poprawności strony.

Zobacz: http://web.archive.org/web/20080913071637/http://www.procheckup.com:80/PDFs/bypassing-dot-NET-ValidateRequest.pdf


Link jest zepsuty.
Peter Mortensen

7

Możesz również użyć funkcji Escape (ciąg znaków) JavaScript, aby zastąpić znaki specjalne. Następnie po stronie serwera użyj serwera. URLDecode (ciąg), aby przełączyć z powrotem.

W ten sposób nie musisz wyłączać sprawdzania poprawności danych wejściowych, a dla innych programistów stanie się jasne, że ciąg może zawierać treść HTML.


7

Skończyłem używać JavaScript przed każdym zwrotnym zwrotnym sprawdzaniem znaków, których nie chciałeś, takich jak:

<asp:Button runat="server" ID="saveButton" Text="Save" CssClass="saveButton" OnClientClick="return checkFields()" />

function checkFields() {
    var tbs = new Array();
    tbs = document.getElementsByTagName("input");
    var isValid = true;
    for (i=0; i<tbs.length; i++) {
        if (tbs(i).type == 'text') {
            if (tbs(i).value.indexOf('<') != -1 || tbs(i).value.indexOf('>') != -1) {
                alert('<> symbols not allowed.');
                isValid = false;
            }
        }
    }
    return isValid;
}

Przyznaję, że moja strona to głównie wprowadzanie danych i jest bardzo mało elementów, które wykonują zwroty, ale przynajmniej ich dane są zachowywane.


Powinny być duże nawiasy zamiast małych nawiasów. Jak `if (tbs [i] .type == 'text') {` zamiast `if (tbs (i) .type == 'text') {`
Shilpa Soni

5

Możesz użyć czegoś takiego jak:

var nvc = Request.Unvalidated().Form;

Później nvc["yourKey"]powinno działać.


Dzięki, twoja odpowiedź pozwoliła mi zaoszczędzić dużo czasu
habib

4

Dopóki są to tylko znaki „<” i „>” (a nie sam znak podwójnego cudzysłowu) i używasz ich w kontekście takim jak <input value = " this " />, jesteś bezpieczny (podczas gdy dla <textarea > ten </textarea> oczywiście byłbyś narażony). Może to uprościć twoją sytuację, ale do wszystkiego innego użyj jednego z innych opublikowanych rozwiązań.


4

Jeśli chcesz tylko powiedzieć użytkownikom, że <i> nie będą używane, ALE, nie chcesz, aby cały formularz został ponownie przetworzony / wysłany z powrotem (i stracił wszystkie dane wejściowe), czy nie możesz po prostu umieścić walidator wokół pola, aby sprawdzić te (i może inne potencjalnie niebezpieczne) postacie?


post powiedział „walidator” proszę
mxmissile

4

Żadna z sugestii mi nie działała. I tak nie chciałem wyłączać tej funkcji dla całej witryny, ponieważ 99% czasu nie chcę, aby moi użytkownicy umieszczali HTML na formularzach internetowych. Właśnie stworzyłem własną metodę obejścia, ponieważ tylko ja używam tej konkretnej aplikacji. Przekształcam dane wejściowe na HTML w kodzie z tyłu i wstawiam do mojej bazy danych.

Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.