Como evitar el resubmit (reenvío de formulario) al actualizar una página web

Javascript ene. 08, 2020

Volvemos a la carga con un post mas de javascript y atacamos a un problema que si bien es muy común, muy pocos desarrolladores se toman el tiempo de resolverlo, hablamos del reenvío del formulario cuando actualizamos una página, no importa si usas para tu backend un php, node, o lo que sea, aquí tenemos una forma muy sencilla de resolverlo con javascript, vamos allá!

A quien no le ha pasado alguna vez mientras desarrollabas tu aplicación web, ha tocado realizar formularios de cualquier tipo, ya sea para crear una página de contacto, para actualizar una entidad, quizás al recuperar una contraseña y en cualquier infinidad de casos, luego de haber dado click en submit intentas actualizar la página y te aparece un cartelito de estos típico para los usuarios de chrome:

Reenvio de formulario en chrome

Generalmente esto puede ocasionar data duplicada en tu base de datos, ¡solo imagina este problema en tu carrito de compras!

Fuente Giphy

Resolviendo el problema

Bien llegados a este punto, primero vamos a considerar una solución interesante llamada el patrón PRG o también conocido como "POST/REDIRECT/GET", básicamente en lugar de retornar directamente a una página web, la operación POST devuelve un comando de redireccionamiento (30x), después de esto automáticamente es solicitado al servidor una petición GET donde finalmente es devuelto a una página de confirmación.

Para mostrarlo gráficamente tenemos esta imagen:

Patrón PRG (Wikipedia)

Este patrón se ha utilizado durante mucho tiempo cuando se presenta el problema de reenvio al desarrollar páginas web, es una forma muy inteligente de resolverlo, la única anotación que debo dejar en claro y que debes notar es que se debe hacer una llamada extra al servidor, luego de esto no hay ningún tipo de problema, puedes darle un vistazo más en este enlace, bien, en las lineas siguientes veremos como resolverlo de otra forma que también es muy practica.

Un método simple con javascript

Todos los navegadores actuales utilizan esta tecnología y prácticamente javascript esta hasta en la sopa, entonces podemos apalancarnos de eso para olvidarnos de la infinidad de dolores de cabeza y evitar el reenvío de solicitudes POST en formularios. Miremos el siguiente código:

if (window.history.replaceState) { // verificamos disponibilidad
    window.history.replaceState(null, null, window.location.href);
}
Reemplazando el estado del historial

Empecemos con window.history que se encarga de devolvernos una referencia al objeto History, a través de él podemos acceder al historial de sesión del navegador y manipularlo, si exactamente, ese historial que nos indica que páginas visitaste o en que página actualmente nos encontramos.

Dentro de ese objeto tenemos disponible la función replaceState, que como su mismo nombre lo indica reemplaza el estado de historial, lo único de que nos pide son 3 parámetros: objeto/null para el estado, un titulo, y una URL, en este último parámetro debemos pasar la url actual.

Este pedazo de código debe ser agregado para que sea llamado cada vez que cargue la página donde esta tu formulario, así de simple, ahora ya puedes pedir correos electrónicos, actualizar tus categorías, enviar respuestas de tu cuestionario, etc y almacenarlo en mysql, postgres, o cualquier bd que estes utilizando, sin preocuparte de la duplicidad de la información que viene desde tu frontend.

Para irnos a comer

Si bien el método es muy interesante y rápido de utilizar, siempre considera de que sólo funciona cuando el navegador web tiene javascript activado, si un usuario desactiva intencionalmente el javascript, el doble submit se realizará aunque no lo quieras. Así que úsalo según tus circunstancias, de todas formas no deja de ser una buena alternativa del patron PRG.

Y eso es todo!, si crees que este artículo te ha proporcionado información de valor, no olvides compartirlo en tus redes sociales para ayudar a otras personas, y no olvides dejar un comentario, amamos saber que opinas! Nos vemos en otra entrega!

Fuente Giphy

Fernando Palacios

¡Hoy es un gran día para hacer grandes cosas!

¡Genial! Te has suscrito con éxito.
¡Genial! Ahora, completa el checkout para tener acceso completo.
¡Bienvenido de nuevo! Has iniciado sesión con éxito.
Éxito! Su cuenta está totalmente activada, ahora tienes acceso a todo el contenido.