Pregunta

Cada vez que un usuario publica algo que contenga < o > en una página en mi aplicación web, me sale esta excepción.

No quiero entrar en la discusión acerca de la elegancia de lanzar una excepción o estrellarse a toda una aplicación web porque alguien entró un personaje en un cuadro de texto, pero estoy buscando una elegante manera de manejar esto.

Captura la excepción y muestra

Se ha producido un error, por favor volver atrás y volver a escribir toda su formulario de nuevo, pero esta vez por favor, no utilice <

no parece profesional suficiente para mí.

Deshabilitar post de validación (validateRequest="false") definitivamente evitar este error, pero va a salir de la página vulnerable a una serie de ataques.

Lo ideal:Cuando se produce una devolución de HTML que contiene caracteres restringidos, que el valor expuesto en el Formulario de recogida serán automáticamente la codificación HTML.Por lo que el .Text la propiedad de mi cuadro de texto será something & lt; html & gt;

Hay una manera que puedo hacerlo desde un controlador?

¿Fue útil?

Solución

Creo que lo están atacando desde el ángulo equivocado tratando de codificar todos los datos enviados.

Tenga en cuenta que "<"también puede provenir de otras fuentes externas, como un campo de base de datos, una configuración, un archivo, un feed y así sucesivamente.

Además, "<"no es inherentemente peligroso.Sólo es peligroso en un contexto específico:cuando la escritura de cadenas que no han sido codificados para la salida de HTML (porque de XSS).

En otros contextos diferentes sub-cadenas son peligrosas, por ejemplo, si usted escribe un usuario-URL proporcionada en un enlace, la sub-cadena "javascript:"puede ser peligroso.El carácter de comilla simple en el otro lado es peligroso cuando la interpolación de cadenas en las consultas SQL, pero perfectamente seguro si esto es una parte de un nombre enviados desde un formulario o leer de un campo de base de datos.

La parte inferior de la línea es:usted no puede filtrar aleatorios de entrada de los peligrosos personajes, ya que cualquier personaje puede ser peligroso bajo las circunstancias adecuadas.Usted debe codificar en el punto en que algunos caracteres específicos puede llegar a ser peligroso porque se cruzan en diferentes sub-lenguaje donde ellos tienen un significado especial.Cuando usted escribe una cadena de texto a HTML, usted debe codificar los caracteres que tienen un significado especial en HTML, utilizando el Server.HtmlEncode.Si pasa una cadena a una dinámica de la sentencia SQL, se debe codificar caracteres diferentes (o mejor, dejar que el marco de hacerlo por usted mediante el uso de declaraciones preparadas o similares)..

Cuando estás seguro de HTML-codificar en todas partes pasa las cadenas HTML, a continuación, establezca validateRequest="false" en el <%@ Page ... %> la directiva en su .aspx archivo(s).

En .NET 4 puede que tenga que hacer un poco más.A veces es necesario agregar también <httpRuntime requestValidationMode="2.0" /> a la web.config (referencia).

Otros consejos

Hay una solución diferente a este error si estás usando ASP.NET MVC:

Ejemplo de C#:

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

Ejemplo de Visual Basic:

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

En ASP.NET MVC (a partir de la versión 3), usted puede agregar el AllowHtml el atributo de una propiedad en su modelo.

Se permite una solicitud para incluir el lenguaje de marcado HTML durante modelo de enlace por saltarse la validación de solicitudes para la propiedad.

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

Si usted está en .NET 4.0, asegúrese de agregar esta en su web.config el archivo dentro de la <system.web> etiquetas:

<httpRuntime requestValidationMode="2.0" />

En .NET 2.0, la validación de las solicitudes sólo se aplica a aspx las solicitudes.En .NET 4.0 este fue ampliado para incluir todos las solicitudes.Usted puede volver a sólo la realización de XSS la validación cuando el procesamiento de .aspx especificando:

requestValidationMode="2.0"

Puede deshabilitar la solicitud de validar totalmente especificando:

validateRequest="false"

Para ASP.NET 4.0, puede permitir marcado como entrada para páginas específicas en lugar de todo el sitio por ponerlo todo en un <location> elemento.Esto se asegurará de que todas sus otras páginas son seguras.Usted NO necesita poner ValidateRequest="false" en su .página aspx.

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

Es más seguro para el control de esta en el interior de su web.config, ya que se puede ver en un sitio de nivel que las páginas permiten marcado como entrada.

Usted todavía necesita para validar mediante programación de entrada en las páginas donde validación de la solicitud está deshabilitado.

Las respuestas anteriores son grandes, pero nadie dijo cómo excluir un único campo de ser validado para HTML/JavaScript inyecciones.Yo no sé acerca de las versiones anteriores, pero en MVC3 Beta puede hacer esto:

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

Esto todavía valida todos los campos excepto los excluidos uno.Lo bueno de esto es que sus atributos de validación todavía validar el campo, pero que simplemente no tienen el "potencialmente peligroso Solicitud.Formulario de valor se detectó desde el cliente" excepciones.

La he usado para la validación de una expresión regular.He hecho mi propia ValidationAttribute a ver si la expresión regular es válido o no.Como las expresiones regulares pueden contener algo que se parece a un script, se aplica el código de arriba - la expresión regular está siendo comprobado si es válido o no, pero no si contiene secuencias de comandos o HTML.

En ASP.NET MVC usted necesita para establecer requestValidationMode="2.0" y validateRequest="false" en la web.config, y aplicar un ValidateInput atributo a la acción del controlador:

<httpRuntime requestValidationMode="2.0"/>

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

y

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

Usted puede Codificación de HTML cuadro de texto de contenido, pero lamentablemente eso no detendrá la excepción de que suceda.En mi experiencia no hay ninguna manera alrededor, y usted tiene que deshabilitar la página de validación.Por que estás haciendo, diciendo:"Tendré cuidado, lo prometo".

Para MVC, ignorar validación de entrada mediante la adición de

[ValidateInput(false)]

encima de cada Acción en el Controlador.

Usted puede coger el error Global.asax.Todavía quiero validar, pero mostrar un mensaje apropiado.En el blog se enumeran a continuación, un ejemplo de como esto estaba disponible.

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

Redireccionar a otra página también parece una respuesta razonable a la excepción.

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

La respuesta a esta pregunta es simple:

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

Este sería deshabilitar la validación de la solicitud en particular.

Por favor, tenga en cuenta que algunos .NET controla automáticamente HTML codificar la salida.Por ejemplo, la configuración de la .Propiedad Text de un control de cuadro de texto automáticamente codificar.Que significa específicamente la conversión de < en &lt;, > en &gt; y & en &amp;.Así que tenga cuidado de hacer esto...

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

Sin embargo, la .Propiedad texto de Hipervínculo, Literal y la Etiqueta de no codificación de HTML cosas, de manera de envolver el Servidor.HtmlEncode();alrededor de todo lo que se establece en estas propiedades es una necesidad si usted quiere evitar <script> window.location = "http://www.google.com"; </script> de salida en la página y posteriormente ejecutado.

Hacer de experimentar un poco para ver lo que se codifica y lo que no.

En la web.archivo de configuración, dentro de las etiquetas, introduzca el httpRuntime elemento con el atributo requestValidationMode="2.0".Agregar también el validateRequest="false" atributo en las páginas elemento.

Ejemplo:

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

Si usted no desea deshabilitar ValidateRequest usted necesidad de aplicar una función de JavaScript con el fin de evitar la excepción.No es la mejor opción, pero funciona.

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

A continuación, en el código de detrás, en el PageLoad evento, agregue el atributo a su control con el siguiente código:

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

Parece que nadie ha mencionado a los de abajo, pero se corrige el problema, para mí.Y antes de que alguien dice que sí que es Visual Basic...puaj.

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

No sé si hay inconvenientes, pero para mí esto funcionó increíble.

Otra solución es:

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

Si usted está utilizando el framework 4.0, a continuación, la entrada en la web.config (<pages validateRequest="false" />)

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

Si usted está utilizando el framework 4.5, a continuación, la entrada en la web.config (requestValidationMode="2.0")

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

Si quieres que sólo una sola página, a continuación, En que archivo aspx usted debe poner la primera línea como esta :

<%@ Page EnableEventValidation="false" %>

si usted ya tiene algo como <%@ Page simplemente añada el resto => EnableEventValidation="false" %>

Yo recomiendo no hacerlo.

En ASP.NET usted puede capturar la excepción y hacer algo al respecto, como la visualización de un mensaje amistoso o redirigir a otra página...También hay una posibilidad de que usted puede manejar la validación por ti mismo...

Mostrar mensaje amistoso:

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

Supongo que se podría hacer en un módulo;pero que deja abiertas algunas preguntas;lo que si desea guardar la entrada a una base de datos?De repente porque vas a guardar los datos codificados en la base de datos que terminan por confiar en la entrada de ella, que es probablemente una mala idea.Lo ideal es almacenar crudo sin codificar los datos en la base de datos y la codificación de cada momento.

Desactivación de la protección en cada nivel de página y, a continuación, la codificación de cada momento, es una mejor opción.

En lugar de utilizar el Servidor.HtmlEncode que usted debe buscar en la nueva, más completa Anti-XSS biblioteca desde Microsoft ACE team.

He encontrado una solución que utiliza JavaScript para codificar los datos, que es decodificado en .NET (y no requiere de jQuery).

  • Hacer el cuadro de texto de un elemento HTML (como textarea) en lugar de un ASP uno.
  • Añadir un campo oculto.
  • Agregue la siguiente función JavaScript a su cabecera.

    la función de boo() { targetText = documento.getElementById("HiddenField1");sourceText = documento.getElementById("userbox");targetText.valor = escape(sourceText.innerText);}

En su área de texto, incluir un onchange que llama boo():

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

Finalmente, en .NET, uso

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

Soy consciente de que esta es una-manera - si usted necesita de dos vías tendrás que ser creativo, pero esto proporciona una solución si usted no puede modificar el web.config

He aquí un ejemplo, yo (MC9000) comenzó con el uso a través de 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
    });


});

Y el lenguaje:

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

Esto funciona muy bien.Si un hacker intenta post a través de omitir JavaScript, que se acaba de ver el error.Usted puede guardar todos los datos codificados en una base de datos y, a continuación, unescape (en el lado del servidor), y analizar y comprobar los ataques antes de que se muestre en otros lugares.

Causa

ASP.NET por defecto valida todos los controles de entrada para potencialmente peligrosos contenidos que pueden conducir a cross-site scripting (XSS) y Las inyecciones de SQL.Por lo tanto se desestima dicho contenido por el lanzamiento de la anterior excepción.Por defecto, se recomienda dejar este cheque a suceder en cada postback.

Solución

En muchas ocasiones necesitas enviar contenido HTML a tu página a través de cuadros de texto Enriquecido o Editores de Texto Enriquecido.En el caso de que usted puede evitar esta excepción en la configuración de la ValidateRequest etiqueta en la @Page la directiva a false.

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

Esto deshabilitará la validación de las solicitudes de la página que han creado la ValidateRequest de bandera falsa.Si desea desactivar esta opción, compruebe lo largo de la aplicación web;usted necesitará establecer a false en tu web.config <system.web> sección

<pages validateRequest ="false" />

Para .NET 4.0 o superior de los marcos también tendrá que añadir la siguiente línea en el <system.web> sección para hacer el trabajo por encima.

<httpRuntime requestValidationMode = "2.0" />

Eso es todo.Espero que esto le ayuda a deshacerse de la cuestión anterior.

Referencia: ASP.Net Error:Potencialmente peligrosa Solicitud.Formulario de valor se detectó desde el cliente

Las otras soluciones de aquí es muy amable, sin embargo es un poco de un dolor real en el trasero a tener que aplicar [AllowHtml] para cada uno de los modelos de propiedad, especialmente si usted tiene más de 100 modelos en un tamaño decente sitio.

Si como yo, desea activar esta (en mi humilde opinión bastante inútil) función de apagado todo el sitio, usted puede reemplazar el método Execute() en el controlador de la base (si usted no tiene un controlador de base le sugiero que haga una, que puede ser bastante útil para la aplicación de la funcionalidad común).

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

Sólo asegúrese de que usted está HTML codificación de todo lo que es bombeada hacia los puntos de vista que provenía de la entrada del usuario (es el comportamiento por defecto en ASP.NET MVC 3 con maquinilla de Afeitar de todos modos, así que a menos que por alguna extraña razón que usted está usando Html.Raw() que no requieren esta característica.

Yo estaba recibiendo este error también.

En mi caso, un usuario introduce un carácter acentuado á en un Nombre de Función (con respecto a la ASP.NET proveedor de pertenencia).

Me pase el nombre de la función a un método para otorgar a los Usuarios que el papel y la $.ajax solicitud post estaba fallando miserablemente...

Hice esto para resolver el problema:

En lugar de

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

Hacer esto

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

@Html.Raw hizo el truco.

Me estaba poniendo el nombre de la Función como valor HTML roleName="Cadastro b&#225;s".Este valor con HTML entidad &#225; estaba siendo bloqueado por ASP.NET MVC.Ahora tengo la roleName el valor del parámetro de la forma en que debe ser: roleName="Cadastro Básico" y ASP.NET MVC motor no se bloquea la petición más.

Deshabilitar la página de validación de si realmente es necesario que los caracteres especiales como, >, , <, etc.A continuación, asegúrese de que cuando el usuario de entrada se muestra, los datos son codificados en HTML.

Existe una vulnerabilidad de seguridad con la página de validación, por lo que puede ser evitado.También la página de validación no debe ser el único invocado.

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

Usted podría también utilizar JavaScript de escape(string) función para reemplazar los caracteres especiales.A continuación, el servidor de uso del lado del Servidor.URLDecode(string) para cambiar de nuevo.

De esta manera usted no tiene que desactivar la validación de las entradas será más claro para que otros programadores que la cadena puede tener contenido HTML.

Terminé usando JavaScript antes de cada postback para comprobar los caracteres que no quieren, tales como:

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

De acuerdo a mi página es principalmente la entrada de datos, y hay muy pocos elementos que hacen que las devoluciones, pero al menos sus datos se mantienen.

Mientras estos son sólo "<"y ">" (y no el doble de la oferta en sí) caracteres y los están usando en contexto como este"/>, usted está seguro (mientras que para <textarea>este</textarea> usted sería vulnerable, por supuesto).Que pueden simplificar su situación, pero para nada más utilice uno de otro publicado las soluciones.

Si usted simplemente está buscando para decirle a sus usuarios que < y > no son para ser utilizado, PERO, usted no desea que el formulario en su totalidad procesados/publicado (y perder toda la entrada) antes de la mano ¿no podría simplemente poner en un validador de todo el campo de la pantalla para aquellos (y tal vez de otros potencialmente peligrosos) caracteres?

Ninguna de las sugerencias que trabajó para mí.Yo no quiero desactivar esta característica para todo el sitio web, de todos modos porque el 99% del tiempo no quiero que mis usuarios colocar el código HTML de web forms.Acabo de crear mi propio trabajo alrededor de método ya que yo soy el único uso de esta aplicación en particular.Puedo convertir la entrada a HTML en el código detrás y lo inserte en mi base de datos.

Usted puede usar algo como:

var nvc = Request.Unvalidated().Form;

Más tarde, nvc["yourKey"] debería funcionar.

Licenciado bajo: CC-BY-SA con atribución
No afiliado a StackOverflow
scroll top