Unobtrusive Ajax en MVC3

Buenas! Una de las novedades más interesantes de MVC3 es el soporte para eso que se llama Unobtrusive Ajax. La verdad es que no encuentro una buena traducción para Unobtrusive (discreto no me convence).

La idea del Unobtrusive Ajax es evitar mezclar código script con código HTML. De la misma manera que CSS nos permite separar completamente el código HTML de su representación, con Unobtrusive Ajax vamos a poder separar el código javascript del código HTML.

Pero mejor, veamoslo con un ejemplo, ultra sencillo 🙂

Imaginad que tengo una vista con este contenido:

<h2>Normal Ajax</h2>
<% using (Ajax.BeginForm("PostData", new AjaxOptions() { HttpMethod="Post", UpdateTargetId="datadiv"})) { %>

<label for="name">Name: </label>
<input type="text" name="name" id="name"/>
<input type="submit" value="Send" />
<% } %>
<hr />
Aquí irá el resultado: <p />
<div id="datadiv">
</div>

Esta vista genera un <form> con un campo de texto y envía los datos a una acción llamada “PostData” e incrusta el resultado de dicha acción (que será una vista parcial) en el div cuyo id es “datadiv”.

Este es el código HTML generado por esta vista en MVC2:

<h2>Normal Ajax</h2>
<form action="/Home/PostData" method="post"
onclick="Sys.Mvc.AsyncForm.handleClick(this, new Sys.UI.DomEvent(event));"
onsubmit="Sys.Mvc.AsyncForm.handleSubmit(this, new Sys.UI.DomEvent(event), { insertionMode: Sys.Mvc.InsertionMode.replace, httpMethod: &#39;Post&#39;, updateTargetId: &#39;datadiv&#39; });">
<label for="name">Name: </label>
<input type="text" name="name" id="name"/>
<input type="submit" value="Send" />
</form>
<hr />
Aquí irá el resultado: <p />
<div id="datadiv">
</div>

Fijaos en que en el tag <form> se le ha incrustado código javascript para gestionar el onclick y el onsubmit (para poder realizar el envío via ajax).

Bien… y esta misma vista (idéntica) que código genera en MVC3? Pues el siguiente:

<h2>Normal Ajax</h2>
<form action="/Home/PostData"
data-ajax="true" data-ajax-method="Post" data-ajax-mode="replace"
data-ajax-update="#datadiv" method="post">

<label for="name">Name: </label>
<input type="text" name="name" id="name"/>
<input type="submit" value="Send" />
</form>

<hr />
Aquí irá el resultado: <p />
<div id="datadiv">
</div>

Fijaos que diferencia… No hay nada de javascript mezclado en el código. Todo es HTML. Simplemente al tag <form> se le añaden unos cuantos atributos (los que empiezan por data-ajax) que indican como se debe comportarse este formulario a nivel de Ajax.

Y quien realiza “la magia”? Pues quien va a ser… nuestra amada jQuery, junto con una extensión de Microsoft (el fichero jquery.unobtrusive-ajax.js)! Para que esto funciona teneis que añadir tanto jQuery como la extensión de MS (yo los pongo en la master):

<script src="<%: Url.Content("~/Scripts/jquery-1.4.1.js") %>" type="text/javascript"></script>
<script src="<%: Url.Content("~/Scripts/jquery.unobtrusive-ajax.js") %>" type="text/javascript"></script>

Esta adaptación de los helpers en MVC3 para soportar esta característica es a lo que nos referimos cuando decimos que “ASP.NET MVC3 da soporte para Unobtrusive Ajax”, y es una doble gran noticia. Digo doble porque por un lado nos permite seguir usando los helpers con la garantía de que vamos a generar código “limpio” de javascript y por otro lado el helper de Ajax usa ¡por fin! jQuery. A diferencia de MVC2 donde el Helper Ajax usaba la Ajax Library de Microsoft. De hecho, aunque en los templates de proyecto se sigue poniendo, si me aceptas un consejo: bórrala y no la uses. Puedes borrarla con total tranquilidad porque en MVC3 ningún helper la usa.

Unobtrusive Ajax viene habilitado por defecto en los nuevos proyectos MVC3 pero lo podéis deshabilitar (y entonces generar el mismo código que en MVC2, usando la Microsoft Ajax Library). Podeis deshabilitarlo a nivel de vista o para todo el proyecto.

Para deshabilitarlo a nivel de vista, basta con incluir:

<% HtmlHelper.UnobtrusiveJavaScriptEnabled = false; %>

Para deshabilitarlo para todo el proyecto, puedes incluir ese mismo código en el global.asax.cs o bien usar web.config:

<configuration>
<appSettings>
<add key="UnobtrusiveJavaScriptEnabled" value="false"/>
</appSettings>
</configuration>

Lo mismo para habilitarlo. Si no aparece la entrada UnobtrusiveJavaScriptEnabled en el <appSettings> el valor por defecto es false. Es por eso que si haces un upgrade de un proyecto de MVC2 a MVC3, no tendrás esta entrada en el web.config y por eso Unobtrusive Ajax estará deshabilitado!

Un saludo!

PD: El hecho de que los atributos que se usan para que Unobtrusive Ajax funcione empiecen por “data-“ es porque HTML5 reserva estos atributos “para usos propios de los scripts del site”, tal y como podéis leer en la especificación de Custom Data Attributes.

5 comentarios en “Unobtrusive Ajax en MVC3”

  1. Estupendo post, Eduard!

    La unobstrusivización (je!) en MVC3 tiene buena pinta. Al independizar la implementación script de ajax y validaciones, nos permitiría usar cualquier librería o incluso implementaciones propias… pero en la práctica significa y demuestra el reinado absoluto de jQuery en el cliente, como debe ser 🙂

    Saludos.

  2. Buenas!
    Lo que me gusta de como lo han enfocado es que usan los custom data attributes de HTML5, por lo que si en un futuro, decidimos NO usar jQuery e irnos a otro sistema, nos servirá cualquier otra librería, siempre y cuando lea esos mismos atributos.
    Conseguimos así una “cierta” independencia del framework javascript en cliente (aunque a efectos prácticos jQuery sea, con merecimiento, el standard de facto).
    No me estrañaría que en un futuro se terminen creando “convenciones estándares de facto” de custom data attributes… veremos 🙂

    Un saludo y gracias por el comentario!!! 😉

Deja un comentario

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *