JavaScript: validación del lado del cliente frente al lado del servidor

179

¿Qué es mejor hacer la validación del lado del cliente o del servidor?

En nuestra situación estamos usando

  • jQuery y MVC.
  • Datos JSON para pasar entre nuestra Vista y el Controlador.

Gran parte de la validación que hago es validar datos a medida que los usuarios ingresan. Por ejemplo, utilizo el keypressevento para evitar letras en un cuadro de texto, establecer un número máximo de caracteres y que un número esté dentro de un rango.

Supongo que la mejor pregunta sería: ¿Hay algún beneficio al hacer la validación del lado del servidor sobre el lado del cliente?


Awesome responde a todos. El sitio web que tenemos está protegido con contraseña y para una pequeña base de usuarios (<50). Si no están ejecutando JavaScript, enviaremos ninjas. Pero si estuviéramos diseñando un sitio para todos, estaría de acuerdo en hacer la validación en ambos lados.

Brad8118
fuente
2
JavaScript se puede deshabilitar
Enrico Murru
No hay una forma segura de bloquear a los usuarios que deshabilitan JavaScript. Si el usuario llega a su página con JS habilitado y luego lo desactiva, no hay nada que pueda hacer. (OK, podría usar JS para implementar el control de envío, de modo que deje de funcionar en este escenario, pero esto se puede omitir como todo lo demás.)
Stewart

Respuestas:

347

Como otros han dicho, debes hacer ambas cosas. Este es el por qué:

Lado del cliente

Desea validar la entrada en el lado del cliente primero porque puede dar una mejor retroalimentación al usuario promedio . Por ejemplo, si ingresan una dirección de correo electrónico no válida y se mueven al siguiente campo, puede mostrar un mensaje de error de inmediato. De esa forma, el usuario puede corregir cada campo antes de enviar el formulario.

Si solo valida en el servidor, tienen que enviar el formulario, recibir un mensaje de error e intentar localizar el problema.

(Este problema puede aliviarse haciendo que el servidor vuelva a procesar el formulario con la entrada original del usuario completada, pero la validación del lado del cliente es aún más rápida).

Lado del servidor

Desea validar en el lado del servidor porque puede proteger contra el usuario malintencionado , que puede omitir fácilmente su JavaScript y enviar información peligrosa al servidor.

Es muy peligroso confiar en tu interfaz de usuario. No solo pueden abusar de su interfaz de usuario, sino que pueden no estar utilizando su interfaz de usuario en absoluto, o incluso un navegador . ¿Qué sucede si el usuario edita manualmente la URL, o ejecuta su propio Javascript, o ajusta sus solicitudes HTTP con otra herramienta? ¿Qué sucede si envían solicitudes HTTP personalizadas desde curlo desde un script, por ejemplo?

( Esto no es teórico; por ejemplo, trabajé en un motor de búsqueda de viajes que volvió a enviar la búsqueda del usuario a muchas aerolíneas asociadas, compañías de autobuses, etc., enviando POSTsolicitudes como si el usuario hubiera llenado el formulario de búsqueda de cada compañía, luego reunido y ordenado todos los resultados. El formulario JS de esas compañías nunca se ejecutó, y fue crucial para nosotros que proporcionaran mensajes de error en el HTML devuelto. Por supuesto, una API hubiera sido agradable, pero esto era lo que teníamos que hacer ) .

No permitir eso no solo es ingenuo desde el punto de vista de la seguridad, sino también no estándar: se debe permitir que un cliente envíe HTTP por cualquier medio que desee, y usted debe responder correctamente. Eso incluye validación.

La validación del lado del servidor también es importante para la compatibilidad : no todos los usuarios, incluso si están usando un navegador, tendrán habilitado JavaScript.

Anexo - Diciembre de 2016

Hay algunas validaciones que ni siquiera se pueden hacer correctamente en el código de aplicación del lado del servidor, y son completamente imposibles en el código del lado del cliente , porque dependen del estado actual de la base de datos. Por ejemplo, "nadie más ha registrado ese nombre de usuario", o "la publicación de blog que está comentando aún existe", o "ninguna reserva existente se superpone a las fechas que solicitó", o "el saldo de su cuenta todavía tiene suficiente para cubrir esa compra ". Solo la base de datos puede validar de manera confiable los datos que dependen de datos relacionados. Los desarrolladores regularmente arruinan esto , pero PostgreSQL proporciona algunas buenas soluciones .

Nathan Long
fuente
30
Esta debería ser la respuesta aceptada, incluso 6 años después: P
Jacob McKay
17
Sí, quería esperar casi 10 años para estar seguro.
Brad8118
2
@kidmosey "es una violación obvia de los principios DRY" Sí, lo que significa dolor para los programadores como nosotros. Pero imagina un formulario de registro. Si duplicar el conocimiento "una dirección de correo electrónico debe contener una @" en el código del cliente significa que los usuarios obtienen comentarios más rápidos y más de ellos se registran, lo que resulta en ingresos adicionales de $ 100k por año, más que paga los costos de mantenimiento adicionales. DRY es un muy buen principio, pero no es la única consideración. La calidad del código se mide realmente en lo bien que sirve a los usuarios y a una organización en un análisis de costo / beneficio.
Nathan Long
1
@ArunRaaj Sí, y captará la mayoría de los problemas de esa manera, pero no es 100% confiable. Si dos usuarios completan el formulario al mismo tiempo, se les puede decir a ambos que user1es un nombre de usuario disponible. Cuando envían, ambos obtendrán el mismo nombre de usuario a menos que vuelva a verificar el lado del servidor. E incluso una verificación en el código de la aplicación del servidor puede tener el mismo problema: entran dos solicitudes, la primera verifica la base de datos y se le dice OK, la segunda verifica la base de datos y se le dice OK, la primera se guarda, la segunda se guarda como un duplicado Solo una restricción db única garantiza la unicidad.
Nathan Long
1
Las validaciones de @NathanLong en datos sensibles a las condiciones de carrera no son tan insolubles como esta frase las hace sonar. Es difícil hacerlo correctamente, pero cree un mecanismo de reserva que use un recurso sincronizado para solicitarlo. Entonces, si el usuario escribe "nombre de usuarioA", una comprobación de unicidad en el servidor que no permite múltiples llamadas simultáneas para verificar si es única; si es único, también resérvelo con un token temporal asignado al cliente que también se libera si el mismo ID de sesión prueba un nombre de usuario diferente. El token debe caducar después de un tiempo razonable. Ejemplo: reserva de asiento TicketMaster.
Elaskanator
79

Sí, la validación del lado del cliente puede omitirse totalmente, siempre. Debe hacer ambas cosas, el lado del cliente para proporcionar una mejor experiencia de usuario, y el lado del servidor para asegurarse de que la entrada que recibe esté realmente validada y no solo supuestamente validada por el cliente.

Vinko Vrsalovic
fuente
43

Solo voy a repetirlo, porque es bastante importante:

Validar siempre en el servidor

y agregue JavaScript para la capacidad de respuesta del usuario.

Toby Hede
fuente
31

El beneficio de hacer la validación del lado del servidor sobre la validación del lado del cliente es que la validación del lado del cliente se puede omitir / manipular:

  • El usuario final podría tener JavaScript desactivado
  • Los datos podrían ser enviados directamente a su servidor por alguien que ni siquiera está utilizando su sitio, con una aplicación personalizada diseñada para hacerlo.
  • Un error de Javascript en su página (causado por cualquier cantidad de cosas) podría ocasionar que se ejecute parte de su validación, pero no toda.

En resumen: siempre, siempre valide el lado del servidor y luego considere la validación del lado del cliente como un "extra" adicional para mejorar la experiencia del usuario final.

Robar
fuente
18

Siempre debe validar en el servidor.

También tener validación en el cliente es bueno para los usuarios, pero es completamente inseguro.

Peter Boughton
fuente
9

Bueno, todavía encuentro espacio para responder.

Además de las respuestas de Rob y Nathan, agregaría que tener validaciones del lado del cliente es importante. Cuando aplique validaciones en sus formularios web, debe seguir estas pautas:

Lado del cliente

  1. Debe usar validaciones del lado del cliente para filtrar solicitudes genuinas provenientes de usuarios genuinos en su sitio web.
  2. La validación del lado del cliente debe usarse para reducir los errores que pueden ocurrir durante el procesamiento del lado del servidor.
  3. La validación del lado del cliente debe usarse para minimizar los viajes de ida y vuelta del lado del servidor para que pueda ahorrar ancho de banda y las solicitudes por usuario.

Lado del servidor

  1. NO DEBE asumir que la validación realizada con éxito en el lado del cliente es 100% perfecta. No importa, incluso si sirve a menos de 50 usuarios. Nunca se sabe cuál de sus usuarios / empleados se convierte en un "malvado" y realiza alguna actividad dañina sabiendo que no tiene las validaciones adecuadas.
  2. Incluso si es perfecto en términos de validación de dirección de correo electrónico, números de teléfono o verificación de algunas entradas válidas, puede contener datos muy dañinos. Que debe filtrarse en el lado del servidor sin importar si es correcto o incorrecto.
  3. Si se omite la validación del lado del cliente, sus validaciones del lado del servidor vienen a rescatarlo de cualquier daño potencial al procesamiento del lado del servidor. En los últimos tiempos, ya hemos escuchado muchas historias de inyecciones SQL y otro tipo de técnicas que podrían aplicarse para obtener algunos beneficios malvados.

Ambos tipos de validaciones juegan papeles importantes en su ámbito respectivo, pero el más fuerte es el lado del servidor. Si recibe 10k usuarios en un solo punto de tiempo, definitivamente terminará filtrando la cantidad de solicitudes que llegan a su servidor web. Si descubre que hubo un solo error, como una dirección de correo electrónico no válida, volverá a publicar el formulario y le pedirá a su usuario que lo corrija, lo que definitivamente consumirá los recursos y el ancho de banda de su servidor. Así que mejor aplica la validación de JavaScript. Si JavaScript está deshabilitado, la validación del lado del servidor vendrá a rescatarlo y apuesto a que solo unos pocos usuarios podrían haberlo deshabilitado accidentalmente ya que el 99.99% de los sitios web usan JavaScript y ya está habilitado de forma predeterminada en todos los navegadores modernos.

KMX
fuente
He visto a personas descuidar la protección contra la inyección de código por completo, no importa hacerlo solo del lado del cliente. Y ninguna referencia a la inyección de código está completa sin un enlace a esto: xkcd.com/327 :)
Stewart
8

Puede realizar la validación del lado del servidor y enviar un objeto JSON con los resultados de validación para cada campo, manteniendo el Javascript del cliente al mínimo (solo mostrando resultados) y aún teniendo una experiencia fácil de usar sin tener que repetirlo tanto en el cliente como en el servidor.

Jonathan
fuente
3
¿Fácil de usar? Tal vez. ¿Casi instantáneo y suave como la mantequilla? Probablemente no.
quadrupleslap
4

El lado del cliente debe usar una validación básica a través de tipos de entrada HTML5 y atributos de patrón, ya que estos solo se usan para mejoras progresivas para una mejor experiencia del usuario (incluso si no son compatibles con <IE9 y safari, pero no confiamos en ellos). Pero la validación principal debería ocurrir en el lado del servidor.

adardesign
fuente
"Pero la validación principal debería ocurrir en el lado del servidor". No debería, debe.
Stewart
2

JavaScript se puede modificar en tiempo de ejecución.

Sugiero un patrón para crear una estructura de validación en el servidor y compartir esto con el cliente.

Necesitará una lógica de validación separada en ambos extremos, por ejemplo:

"required"atributos en inputsel lado del cliente

field.length > 0 lado del servidor.

Pero el uso de la misma especificación de validación eliminará cierta redundancia (y errores) de la validación de duplicación en ambos extremos.

TaylorMac
fuente
2

La validación de datos del lado del cliente puede ser útil para una mejor experiencia de usuario: por ejemplo, si un usuario que escribe incorrectamente su dirección de correo electrónico, no debería esperar hasta que un servidor remoto procese su solicitud para conocer el error tipográfico que hizo.

Sin embargo, como un atacante puede pasar por alto la validación del lado del cliente (y puede que incluso no use el navegador), se requiere la validación del lado del servidor, y debe ser la puerta de entrada real para proteger su backend de los usuarios nefastos.

Billal Begueradj
fuente
1

Encontré un enlace interesante que hace una distinción entre errores burdos, sistemáticos y aleatorios.

Client-Side validationse adapta perfectamente para prevenir errores graves y aleatorios. Típicamente una longitud máxima para textura y entrada. No imite la regla de validación del lado del servidor; proporcione su propia regla general de validación de la regla general (por ejemplo, 200 caracteres en el lado del cliente; nen el lado del servidor dictado por una regla comercial sólida).

Server-side validationse adapta perfectamente para prevenir errores sistemáticos; hará cumplir las reglas comerciales.

En un proyecto en el que estoy involucrado, la validación se realiza en el servidor a través de solicitudes ajax. En el cliente muestro mensajes de error en consecuencia.

Lectura adicional: errores brutos, sistemáticos y aleatorios:

https://answers.yahoo.com/question/index?qid=20080918203131AAEt6GO

Roland
fuente
-2

Si está realizando una validación ligera, es mejor hacerlo en el cliente. Ahorrará el tráfico de red que ayudará a que su servidor funcione mejor. Si se trata de una validación complicada que implica extraer datos de una base de datos o algo así, como contraseñas, lo mejor es hacerlo en el servidor donde los datos se pueden verificar de forma segura.

Tom
fuente
2
Lo que estás diciendo no es la mejor idea. El usuario siempre puede omitir la validación del lado del cliente y enviar lo que quiera a la base de datos.
kremuwa