Optimización AJAX 1: elección del método HTTP

Si bien las interacciones en AJAX nos permiten obtener información de forma dinámica desde el servidor de un sitio web o aplicación, existen varias formas de aumentar la velocidad de estas respuestas para mejorar la experiencia de nuestros usuarios al cargar información bajo demanda, obtener datos de búsquedas u otras interacciones.

Más allá de la parafernalia tecnológica que supone la implementación de una respuesta AJAX (por supuesto, reducida al mínimo con el uso de un framework adecuado), ésta sigue siendo una respuesta HTTP, por lo que se pueden aplicar los mismos principios para mejorar su performance.

En éste y los siguientes posts intentaré revisar la teoría y práctica de las técnicas fundamentales para mejorar la performance de respuestas AJAX y la experiencia de tus usuarios.

Elección del método de respuesta

La primera regla es (o debería ser) casi obvia, por lo que vamos directo al grano: al ejecutar una petición AJAX, debes hacerlo con el método (verbo) HTTP adecuado.

GET para obtener, POST para enviar

Veamos un poco de background: las peticiones HTTP se realizan a través de distintos métodos, llamados también verbos debido a que determinan la acción que se realizará en la petición.

Los verbos más conocidos y que se encuentran implementados de forma más extendida son:

  • GET (obtener) se utiliza para solicitar “la representación de un recurso”. Una petición GET debería obtener data sin ningún otro efecto.
  • POST se utiliza para enviar información al servidor, tal como la información de un formulario de contacto o una nueva entrada de una base de datos.

Existen otros métodos tales como PUT, DELETE, HEAD, OPTIONS, etc; que a pesar de ser parte del estándar no siempre están implementados en alguna parte del stack (servidor web, framework) o son más propensos a ser interceptados por filtros de seguridad, por lo que se suele preferir los dos anteriores — por ello es común que para remediar esto algunas APIs implementen los restantes métodos a través de la cabecera X-HTTP-Method-Override.

Por lo tanto, enviar una petición por GET o POST tiene que ver en primer lugar con una cuestión semántica ya que indica el tipo de acción que vamos a realizar.

Por otra parte, en las peticiones GET toda la información va codificada como parte de la URL, por lo que existe un límite práctico dado por la longitud máxima aceptad por los navegadores. Como es de esperar, Internet Explorer es el que impone el mínimo denominador: 2 Kb.

Finalmente, en términos puramente de performance, en las peticiones POST los navegadores hacen un envío en dos partes: en primer lugar, las cabeceras de la petición y luego los datos; mientras que con GET lo que se envía es solamente la petición, que en la URL incluye todos los parámetros.

Con jQuery tenemos varias formas de implementar los distintos métodos de petición, por ejemplo, utilizando las APIs de más alto nivel, podemos ejecutar directamente uno de ellos:

// Cargar información por GET
$.get( ajaxurl, { action: 'get_latest_comments' }, function(data){
	$('#recent-comments').append( data );
}, 'html');

// Enviar un formulario con POST
$('#contact-form').on('submit', function( event ){
	// Podemos utilizar serialize para recoger toda la información
	// correspondiente a los campos del formulario
	var formdata = $(this).serialize();
	$.post( ajaxurl, formdata, function( reply ){        
		$('#contact-form').prepend( reply.status_message );
	}, 'json' );
	event.preventDefault();
});

Y también podemos utilizar la API de más bajo nivel, que nos permite especificar manualmente el tipo de petición:

$('#contact-form').on('submit', function(event){
	var formdata = $(this).serialize();
	$.ajax({
		type : 'POST',
		data : formdata,
		dataType: 'json',
		success: function( response ){
			$('#contact-form').prepend( response.status_message );
		},
		error: function( response ){
			alert( response.status_message );
		}
	});
	event.preventDefault();
});

Al utilizar jQuery.ajax() tienes la ventaja adicional que puedes indicar qué hacer en caso de errores.