Este es el tercer post de la serie compuesta por:
- 101 citas célebres del mundo de la informática
- Otras 101 citas célebres del mundo de la informática
- Y todavía otras 101 citas célebres del mundo de la informática (este post)
- 101 nuevas citas célebres del mundo de la informática (¡y van 404!)
Publicado por José M. Aguilar a las 5:48 a. m.
Etiquetas: curiosidades, frases célebres, humor
Tobin Harris ha puesto en marcha un curioso e interesante servicio, al que ha denominado yUML, cuyo propósito es facilitar la generación al vuelo de diagramas UML a partir de una concisa descripción expresada en un sencillo lenguaje específico.
Pero además de la generación automática del diagrama UML, que ya tiene mérito de por sí, llama la atención que esto puede realizarse desde una etiqueta (X)HTML <img>
a la que se le envía la especificación como parámetro, generándose en tiempo real una imagen con el diagrama correspondiente. Por ello, está especialmente indicado para autores de blogs, wikis o contenidos web que deseen introducir muy fácilmente estos diagramas en sus creaciones.
En los siguientes ejemplos se muestran la especificación y la imagen generada de un diagrama de clases y uno de casos de uso, respectivamente. Como podréis comprobar, la especificación es bastante legible directamente.
Diagrama de clases
Especificación: [Company]<>-1>[Location], [Location]+->[Point]
Código fuente para su inserción en una página:
<img src="http://yuml.me/diagram/class/[Company]<>-1>[Location], [Location]+->[Point]" />
<img src="http://yuml.me/diagram/scruffy/class/[Company]<>-1>[Location], [Location]+->[Point]" />
Diagrama de casos de uso
Especificación: [User]-(Login), [User]-(Logout), (Login)<(Reminder), (Login)>(Captcha)
Código fuente para su inserción en una página:
<img src="http://yuml.me/diagram/usecase/[User]-(Login), [User]-(Logout), (Login)<(Reminder), (Login)>(Captcha)" />
Si prefieres simplemente descargar el diagrama para subirlo a tu web, opción bastante prudente hasta que se pueda confiar en la fiabilidad y disponibilidad del servicio, desde el mismo sitio web del producto podemos generar la imagen introduciendo la especificación textual; a partir de ahí podremos copiarla y pegarla sobre nuestra herramienta de edición, o salvarla en nuestro equipo para enviarla a su ubicación definitiva.
Si bien todavía yUML está en pruebas y es algo limitado (sólo soporta diagramas de clases y de casos de uso), me ha parecido muy interesante tanto la idea como la implementación del servicio.
Publicado en: Variable not found
Publicado por José M. Aguilar a las 11:05 p. m.
Etiquetas: desarrollo, diseño, dsl, patrones, servicios on-line
Joe Cartano, perteneciente al Visual Web Development Team de Microsoft, ha publicado en el blog oficial (Visual Web Developer Team Blog) un post anunciando que ha actualizado la plantilla que permite crear directamente proyectos ASP.NET MVC con tests unitarios NUnit.
Así, una vez instalado, al crear un proyecto de tipo ASP.NET MVC nos aparecerá un cuadro de diálogo como el siguiente, en el que se nos brindará la oportunidad de crear en la solución un proyecto de pruebas unitarias utilizando NUnit:
Para los poseedores de algunas de las versiones profesionales de Visual Studio 2008, esta ventana no es nueva, puesto que por defecto ya se incluyen los proyectos de tests propios de Microsoft, pero sí lo es para la versión express del IDE, que no incluye el framework de pruebas y en el que había que crear el proyecto a mano.
El proyecto, que se crea automáticamente, realiza 27 tests sobre la plantilla original de proyectos ASP.NET MVC, y pueden servir como base para seguir creando nuestro propio conjunto de pruebas:
La plantilla se instala descargando el archivo .zip cuyo enlace encontraréis en el post original y ejecutando, si es necesario con un usuario con privilegios de administrador, el script installNUnit.cmd
disponible en el raíz del directorio donde lo hayáis descomprimido.
Para que todo vaya bien, debéis contar con NUnit previamente instalado en vuestro equipo. Pero ojo, las plantillas están preparadas para la versión 2.4.8.0 y la versión actual es la 2.5.0.9122, por lo que puede que no os funcionen bien si estáis a la última.
En este caso, es necesario tocar a mano los archivos de plantillas. Podéis seguir estos pasos:
- Descargad el archivo de plantillas desde el blog del Visual Web Developer Team.
- Descomprimidlo sobre cualquier carpeta.
- En los subdirectorios CSharp y Visual Basic encontraréis un archivo llamado
MvcApplication.NUnit.Tests.zip
. Son las plantillas para cada uno de esos lenguajes. - El interior de dicho zip está el archivo de proyecto (
MvcApplication.NUnit.Test.vbproj
en el caso de Visual Basic,MvcApplication.NUnit.Test.csproj
en C#). Descomprimid sólo estos archivos y buscar en ambos la cadena “2.4.8.0” y sustituirla por la versión de NUnit que tengáis instalada (en mi caso, “2.5.0.9122”). Al acabar, actualizad de nuevo el .zip con el archivo que acabáis de editar. - Ejecutad el script de instalación
installNUnit.cmd
.
Publicado en: Variable not found.
Publicado por José M. Aguilar a las 11:45 p. m.
Etiquetas: .net, asp.net, aspnetmvc, buenas prácticas, desarrollo, vs2008
El pasado 8 de mayo, además de conmemorarse el nacimiento de la Coca-Cola, se cumplían tres años desde que publiqué el primer post en este blog. Y me sigue pareciendo que fue ayer, cómo pasa el tiempo…
Como en otras ocasiones, es un bonito momento para recapitular y comentar lo que ha ido ocurriendo por aquí desde entonces.
Durante la celebración del segundo cumpleaños hice una distinción de dos periodos en la historia de Variable not found, que os resumo:
- Año 1: la travesía del desierto (mayo 2006 - mayo 2007), periodo caracterizado principalmente por la ausencia prácticamente total de visitantes al blog, por aquellos tiempos disponible a través de la dirección jmaguilar.blogspot.com. Y no exagero, observad el registro de visitas de los primeros meses, y tened en cuenta que yo mismo también visitaba la página:
Aprovecho para introducir un mensaje de aliento para los que estéis en esta situación ahora, empezando un blog: no os desaniméis, ni aun viendo este desastre. Con un poco de esfuerzo todo puede cambiar. El desierto también tiene su fin.
- Año 2: el despegue (mayo 2007 - mayo 2008), durante el cual se produjeron múltiples novedades, como la adquisición del dominio variablenotfound.com, la difusión de feeds a través de
, el por aquél entonces magnífico,Feedburner, la creación del diseño actual, y la inclusión en agregadores y comunidades como Planeta Código, Planet WebDev y Geeks.ms.Este segundo año lo acabamos con un incremento del 2.500% en el número de visitas (la verdad, tampoco lo tenía muy difícil partiendo desde cero ;-)), y lo que me parecía más increíble, 380 suscriptores.
Y siguiendo esta línea, el año que hemos acabamos ahora podríamos describirlo como:
Año 3: la consolidación (mayo 2008 – mayo 2009)
Aunque ha sido un año sin grandes cambios, Variable not found ha seguido creciendo. Obviamente no en las proporciones anteriores, pero sí ha mostrado un aumento considerable tanto de visitantes como de suscriptores.
Respecto a las visitas a la web, hay que destacar los siguientes datos:
- las visitas, en general, han aumentado cerca de un 40%, así como el número de usuarios únicos absolutos. Hay que tener en cuenta que durante este último año no se han producido meneos espectaculares como el año anterior, no han pasado de meneillos, por lo que la subida de visitas en global tiene bastante mérito.
- También se han incrementado ligeramente el número de páginas vistas por visita, y el tiempo medio en la página.
- El tráfico dirigido desde buscadores se han incrementado en un 75% desde el periodo anterior. Esto podría entenderse como que el blog está logrando un posicionamiento importante en estos motores, probablemente debido a la antigüedad, a las referencias externas y a los propios contenidos.
- Curiosamente, ha disminuido el número de visitantes nuevos en proporción a los que repiten, lo que implica que aumenta el número de usuarios que han visitado el blog más de una vez.
- Los comentarios, como manda la tradición, siguen siendo escasos: la media no llega a dos comentarios por cada post publicado. Nada que objetar en esto, soy el primero al que le cuesta la misma vida comentar algo en blogs ajenos que sigo con asiduidad. Es cierto que me gustaría obtener más feedback y opiniones de los lectores, pero entiendo que no sea así.
En cuanto a las suscripciones, siguen siendo uno de los datos que más me están sorprendiendo, y muy gratamente. En estos momentos, a pesar de los cambios de humor de Feedburner, hemos llegado ya a alcanzar los 650 suscriptores.
Y sinceramente, este es uno de los datos que más valoro. La temática tan específica del blog hace que los destinatarios de los contenidos, principalmente desarrolladores, sean una minoría, y conseguir que un número tan alto de personas decidan voluntariamente añadirte de alguna forma a sus fuentes favoritas es todo un honor y, sin duda, motivo de orgullo.
En el aspecto económico, sigo arrasando con los ingresos por AdSense. El mes pasado, junto con el cheque mensual me enviaron una caja de bombones, con una tarjeta de felicitación firmada por el mismísimo Sergey Brin…
… vaya, parece que me había quedado dormido otra vez ;-D. Pues no, de momento sigo recaudando centimillos a un ritmo lamentable, pero bueno, ¿quién dijo que esto de bloguear se hacía por dinero?
Lo que considero mi recompensa es lo que estoy aprendiendo. Cada tema tratado, ejemplo, referencia, cada comentario, cada mensaje privado recibido, me aportan una nueva oportunidad para ampliar conocimientos. Si esto lo unimos al placer de comunicar y de compartir los descubrimientos, ya tenemos un buen conjunto de motivaciones que animan a seguir trabajando en el blog.
Pero aún falta algo, sin duda lo más importante: vosotros. Los que estáis ahí leyendo, enviando comentarios o mensajes, añadiendo valor a las entradas, los que le dais sentido a todo esto. Repito lo que ya comenté en el post en el que celebraba el primer aniversario:
Os puedo asegurar que he disfrutado escribiendo cada post, pero las alegrías han venido con cada comentario, con cada visita, con cada referencia.
Muchas gracias a todos, y espero que sigáis por aquí, ayudándome a buscar la variable.
Publicado en: Variable not found
Existen numerosas aplicaciones que permiten analizar nuestros desarrollos con el objetivo final de incrementar la calidad de los mismos. FxCop, por ejemplo, es capaz de analizar los ensamblados y avisarnos cuando se encuentra con incumplimientos de las pautas de diseño para desarrolladores de librerías para .Net Framework (Design Guidelines for Class Library Developers). También hace tiempo comenté por aquí la disponibilidad de Microsoft Source Analysis for C#, una herramienta que se centra en el código fuente y el cumplimiento de reglas de codificación.
Ahora, gracias al ofrecimiento de Patrick Smacchia, lead developer del producto, he podido probar NDepend, una herramienta de análisis de código de la que había oído hablar y que va mucho más allá que las citadas anteriormente.
La principal misión de NDepend es ayudarnos a incrementar la calidad de nuestros sistemas desarrollados con .NET mediante el análisis de sus ensamblados y código fuente desde distintas perspectivas, como la complejidad de sus módulos, el tamaño de los mismos, las interdependencias entre ellos, etc. Es decir, a diferencia de otros analizadores, su objetivo no es avisarnos de aspectos como la utilización de convenciones de codificación (aunque también puede hacerlo), o el uso de buenas prácticas de diseño, sino ayudarnos a determinar, por ejemplo, cuándo ponemos en peligro la mantenibilidad y evolución de un sistema debido a la complejidad o al fuerte acoplamiento de algunos de sus componentes, por citar sólo algunos criterios.
El entorno gráfico
VisualNDepend es el entorno gráfico de la herramienta, y nos ofrece un entorno de trabajo muy potente e intuitivo, aunque durante los primeros minutos pueda resultar algo complejo debido a la cantidad de información mostrada.
Iniciar el análisis de un sistema es muy sencillo; una vez seleccionado el ensamblado, conjunto de ensamblados o proyecto a estudiar, el sistema realiza el análisis, del cual se obtiene un informe bastante completo, basado en web, sobre el mismo (podéis ver un ejemplo de informe en la página del producto). En él se recogen:
- métricas de la aplicación, entre las que encontramos el número de líneas de código, comentarios, número de clases, métodos, etc., así como datos estadísticos relativos a la complejidad, extensión y estructura del código.
- métricas por ensamblado, donde se refleja, por cada uno de los ensamblados que componen la solución, datos sobre su tamaño, grados de cohesión, acoplamiento, y otros aspectos relativos a su complejidad e interdependencia.
vista de estructura (captura de la derecha) que muestra la distribución de componentes, la granularidad y su complejidad relativa según el tamaño de los bloques visualizados.
- diagrama de abstracción e inestabilidad, que posiciona cada ensamblado en función del número de clases abstractas e interfaces que presenta y su dependencia del resto de elementos.
- relación entre ensamblados, que detalla las interdependencias entre ensamblados del proyecto, los posibles ciclos, así como un posible orden de generación.
- consultas y restricciones CQL, que realiza una serie de consultas predefinidas sobre los ensamblados y el código que nos ayuda a detectar una infinidad de problemas en nuestros desarrollos, desde aspectos relativamente simples como el exceso de métodos en clases o el incumplimiento de ciertas convenciones de nombrado, hasta problemas en la cobertura de los tests generados con NCover o Visual Studio Team System.
Pero lo mejor del entorno gráfico no es poder generar un análisis en formato web para poder consultarlo más adelante, de hecho esto puede conseguir también con la aplicación de consola que incluye NDepend. Lo mejor son las fantásticas herramientas interactivas que nos permiten navegar a través de nuestras aplicaciones, cambiar de vista, ampliar información sobre cualquier elemento, y realizar consultas en tiempo real, siempre ofreciendo unos resultados muy claros y visuales, como:
- diagrama de dependencias entre todo tipo de elementos, como clases, espacios de nombres, o ensamblados. Resulta muy útil, además, configurar el tamaño de los bloques, el grosor del borde y el de las flechas de unión para que sean proporcionales a la complejidad, tamaño y una larga lista de criterios.
matriz de dependencias, que muestra de forma visual las relaciones de utilización entre espacios de nombres, tipos, métodos o propiedades, con posibilidad de ir ampliando información.
- comparación entre ensamblados, mostrándonos los cambios producidos entre, por ejemplo, dos versiones de una misma librería o aplicación.
- navegación avanzada por el código a través del uso del menú contextual que facilita la rápida localización de referencias, directas e indirectas, hacia y desde un método, propiedad o tipo existente.
- enlace con Reflector, una herramienta indispensable, con la que se integra perfectamente gracias a su plugin.
CQL (Code Query Language)
Sin duda, una de las características más interesante que tiene NDepend es el soporte del lenguaje de consulta CQL (Code Query Language), que nos ofrece la posibilidad de tratar nuestro código y ensamblados como si fuesen una gigantesca base de datos sobre la que podemos realizar consultas de forma muy natural. Las posibilidades que esto ofrece son tan amplias que prácticamente todas las funcionalidades de la aplicación están basadas en órdenes CQL prediseñadas que acompañan al producto, aunque podemos crear todas las consultas personalizadas que necesitemos, como por ejemplo:
/* Obtiene los métodos que escriben una propiedad */
SELECT METHODS WHERE IsDirectlyWritingField "Model.Cliente.Nombre"
/* Obtiene métodos que acceden incorrectamente a los
datos desde la capa de interfaz
*/
SELECT METHODS FROM NAMESPACES "Interfaz" WHERE IsDirectlyUsing "MySql.Data"
/* Obtiene los 10 métodos con más líneas de código */
SELECT TOP 10 METHODS ORDER BY NbLinesOfCode DESC
/* Obtiene los métodos considerados "peligrosos" según su complejidad ciclomática */
SELECT METHODS WHERE CyclomaticComplexity > 20
Además de consultas CQL cuyo resultado podremos observar de forma directa tanto visualmente como en forma de listado, es posible incluir restricciones (WARN) que hará que el sistema nos alerte durante el análisis de un proyecto que cumpla las condiciones especificadas. Por ejemplo, la siguiente restricción nos avisará cuando exista un cierto tufillo a complejidad excesiva en un método (que haya sido definido con más de 10 parámetros):
WARN IF Count > 0 IN SELECT METHODS WHERE NbParameters > 10
Estas consultas pueden ser añadidas (en la versión Pro) e integradas en los análisis, así como modificar las existentes, de forma que el producto puede ser personalizado a nuestras convenciones o necesidades específicas.
Otra posibilidad es incluir dentro del código de un ensamblado las restricciones que deseamos que se cumplan, expresándolas en lenguaje CQL embebido en un atributo de tipo CQLConstraint
aplicado a sus elementos:
Afortunadamente existe mucha información disponible en la web sobre el lenguaje CQL, y consultas que nos muestran cómo sacarle el máximo partido.
Instalación e integraciones
NDepend se distribuye en formato .zip, y que puede ejecutarse directamente una vez descomprimido el contenido sobre una carpeta. La licencia, una vez obtenida, es un archivo XML firmado digitalmente que debemos colocar en el directorio de la aplicación, y listo.
Ya en ejecución, desde el menú “options” es posible configurarlo para que se integre con Visual Studio 2005, 2008 y como he comentado anteriormente, con el magnífico Reflector, con el que hace una excelente pareja.
Asimismo, es posible utilizarlo en sistemas como MSBuild y NAnt, facilitando así su uso en entornos de integración continua y montaje automatizado, para los que ofrece librerías
Finalmente, he de aclarar que NDepend es una aplicación comercial, aunque dispone de una versión limitada gratuita utilizable por universidades, desarrolladores open source e incluso, durante un tiempo determinado, de prueba en proyectos comerciales.
En cualquier caso, no dudéis en probarlo: os dará un control sobre vuestro código difícil de conseguir con otras herramientas.
Publicado en: www.variablenotfound.com
Publicado por José M. Aguilar a las 11:40 p. m.
Etiquetas: .net, antipatrones, buenas prácticas, calidad, desarrollo, herramientas, patrones
Huye como del diablo de aquél que utilice demasiadas veces las palabras:
- Necesitamos
- Debemos
- No podemos
- Sencillo
- Simplemente
- Sólo
- Rápido
… y especialmente si las utiliza en el mismo párrafo.
(Del clásico Four Letter Words –need, must, can’t, easy, just, only, fast- publicado en Signals vs Noise).
Publicado en: www.variablenotfound.com
La combinación de teclas Control-Alt-Suprimir lleva con nosotros prácticamente desde el principio de los tiempos ayudándonos a escapar de callejones sin salida. Y como muchas otras pequeñas cosas de la vida, tiene su curiosa historia por detrás.
David Bradley era uno de los doce ingenieros que trabajaron en el diseño del IBM PC original a principios de los años 80, implementando el código de la ROM BIOS.
El objetivo inicial era crear una combinación de teclas exclusivamente para que los desarrolladores y escritores técnicos pudieran resetear el ordenador en caliente, de forma rápida, puesto que el apagado manual requería la espera de algunos segundos antes de volver a encenderlo para evitar daños a la fuente de alimentación, y cuando esto había que repetirlo muchas veces al día, como era el caso, la pérdida de tiempo era considerable.
De hecho, al principio ni siquiera se pensaba en trasladar esta función a los usuarios finales de estos ordenadores, pero finalmente resultó tan útil y ahorraba tanto tiempo que difundió y popularizó rápidamente entre los usuarios.
La combinación original de teclas era Control-Alt-Escape, pero pensaron que de esa forma alguien podía pulsarlas accidentalmente al encontrarse todas en el lado izquierdo del teclado. Por ello, finalmente se decantaron por una secuencia que era imposible, en los teclados de entonces, reproducir con una única mano. Había nacido el Control-Alt-Suprimir, y para muchos, un icono cultural de nuestros tiempos.
David Bradley también es famoso por la frase que tanto hizo reír a casi todos durante la celebración del 20 aniversario del IBM PC:
“Yo lo inventé, pero Bill lo hizo famoso”
Bradley se retiró en 2004, tras cerca de 29 años trabajando en IBM.
Publicado en: www.variablenotfound.com
En marzo de 2008 publiqué un post en el que se recogían respuestas a diez preguntas básicas sobre el framework ASP.NET MVC, que por aquellos entonces se encontraba todavía en una versión muy preliminar, la Preview 2.
Más de un año después, coincidiendo con el reciente lanzamiento de la versión 1.0, voy a actualizar el contenido y las preguntas conforme a la evolución de los desarrollos y a lo que he podido profundizar en el tema desde entonces.
Las cuestiones que trataré son las siguientes:
- Empecemos desde el principio, ¿qué es MVC?
- ¿Qué ventajas tiene el uso del patrón MVC?
- ¿Qué es ASP.NET MVC framework?
- ¿Es el primer framework MVC creado para .NET?
- Como desarrollador de aplicaciones web con ASP.NET, ¿me afectará la llegada de este framework?
- Entonces, ¿no significa la aparición del framework MVC la muerte próxima de los Webforms de ASP.NET?
- ¿Vale la pena pasarse a ASP.NET MVC o sigo usando Webforms?
- ¿Puedo convertir mi proyecto ASP.NET Webforms a ASP.NET MVC?
- ¿Se puede utilizar ASP.NET Ajax con el framework MVC?
- ¿Se puede utilizar VB.NET con ASP.NET MVC?
- ¿Puedo usar LINQ desarrollando aplicaciones con ASP.NET MVC framework?
- ¿Qué tipo de tecnologías puedo utilizar en las vistas?
- ¿Es ASP.NET MVC framework software libre?
1. Empecemos desde el principio, ¿qué es MVC?
Aunque de forma algo simplista, podríamos definir MVC como un patrón arquitectural que describe una forma de desarrollar aplicaciones software separando los componentes en tres grupos (o capas):- El Modelo que contiene una representación de los datos que maneja el sistema, su lógica de negocio, y sus mecanismos de persistencia.
- La Vista, o interfaz de usuario, que compone la información que se envía al cliente y los mecanismos interacción con éste.
- El Controlador, que actúa como intermediario entre el Modelo y la Vista, gestionando el flujo de información entre ellos y las transformaciones para adaptar los datos a las necesidades de cada uno.
MVC son las siglas de Modelo-Vista-Controlador, y se trata de un modelo muy maduro y que ha demostrado su validez a lo largo de los años en todo tipo de aplicaciones, y sobre multitud de lenguajes y plataformas de desarrollo.
Puedes encontrar más información en:
- Wikipedia, Modelo-Vista-Controlador
- Documentos originales de definición de MVC, de Trygve M. H. Reenskaug, en Xerox (¡año 1978!)
- Tutorial de Java, Arquitectura MVC
- Model-View-Controller Web presentation pattern en MSDN
2. ¿Qué ventajas tiene el uso del patrón MVC?
Como siempre, esto de enumerar ventajas es algo subjetivo, por lo que puede que pienses que falta o sobra alguna (¡dímelo!). En un primer asalto podríamos aportar las siguientes:- Clara separación entre interfaz, lógica de negocio y de presentación, que además provoca parte de las ventajas siguientes.
- Sencillez para crear distintas representaciones de los mismos datos.
- Facilidad para la realización de pruebas unitarias de los componentes, así como de aplicar desarrollo guiado por pruebas (TDD).
- Reutilización de los componentes.
- Simplicidad en el mantenimiento de los sistemas.
- Facilidad para desarrollar prototipos rápidos.
- Los desarrollos suelen ser más escalables.
- Tener que ceñirse a una estructura predefinida, lo que a veces puede incrementar la complejidad del sistema. Hay problemas que son más difíciles de resolver respetando el patrón MVC.
- La curva de aprendizaje para los nuevos desarrolladores se estima mayor que la de modelos más simples como Webforms.
- La distribución de componentes obliga a crear y mantener un mayor número de ficheros.
3. ¿Qué es ASP.NET MVC Framework?
Es un framework, un entorno de trabajo cuya primera versión acaba de ver la luz, creado por Microsoft con objeto de ayudarnos a desarrollar aplicaciones que sigan la filosofía MVC sobre ASP.NET.
Además del conjunto de librerías (ensamblados) que proporcionan las nuevas funcionalidades a nivel de API, incluye plantillas y herramientas que se integran en Visual Studio 2008 (tanto en la versión Express de Visual Web Developer como en sus hermanas mayores) para facilitarnos un poco las cosas.
Una vez instalado el marco de trabajo (que puedes iniciar desde aquí o desde el Web Platform Installer), Visual Studio mostrará un nuevo tipo de proyecto (ASP.NET MVC Web Application) que nos permitirá crear el esqueleto básico de un proyecto de este tipo. Y ya para cuando estemos en faena, el entorno ofrece multitud de utilidades para hacer nuestro trabajo más fácil, como la herramienta de creación de vistas automáticas, el desplazamiento entre controladores y vistas, o plantillas para la definición de controladores, entre otras.
4. ¿Es el primer framework MVC creado para .NET?
No, ni el único. Existen multitud de frameworks MVC para ASP.Net, como MonoRail, Maverick.Net, ProMesh.Net y muchos otros.
5. Como desarrollador de aplicaciones web con ASP.NET, ¿me afectará la llegada de este framework?
No necesariamente. Puedes seguir desarrollando aplicaciones como hasta ahora, con Webforms. Si así lo decides, este nuevo framework no te afectará nada; simplemente, ignóralo.
De todas formas, ya que has leído hasta aquí, permíteme un consejo: aprende a utilizar ASP.NET MVC framework. Después podrás decidir con conocimiento de causa si te conviene o no.
6. Entonces, ¿no significa la aparición del framework MVC la muerte próxima de los Webforms de ASP.NET?
En absoluto. Son simplemente dos filosofías diferentes para conseguir lo mismo, ¡páginas web!
La tecnología de Webforms es muy útil para asemejar el desarrollo de aplicaciones web a las de escritorio, ocultando la complejidad derivada del entorno desconectado y stateless (sin conservación de estado) del protocolo HTTP a base de complejos roundtrips, postbacks y viewstates, lo que nos permite crear de forma muy productiva formularios impresionantes y que el funcionamiento de nuestra aplicación esté guiado por eventos, como si estuviéramos programando Winforms.
Sin embargo, esta misma potencia a veces hace que las páginas sean pesadas y difícilmente mantenibles, además de dificultar enormemente la realización de pruebas automatizadas. Y por no hablar de comportamientos extraños cuando intentamos intervenir en el ciclo de vida de las páginas, por ejemplo para la carga y descarga de controles dinámicos.
ASP.NET MVC propone una forma distinta de trabajar, más cercana a la realidad del protocolo y, curiosamente, más parecida a cómo se hacía unos años atrás, cuando controlábamos cada byte que se enviaba al cliente o se recibía de éste. No existen, por tanto, conceptos como el mantenimiento del estado en el viewstate, ni el postback, ni nos valdrán los controles de servidor basados en estas características, que son la mayoría. Sin embargo, dado que el framework está creado sobre ASP.NET, será posible utilizar páginas maestras, codificar las vistas en un .aspx utilizando C# o VB.NET, usar los mecanismos de seguridad internos, control de caché, gestión de sesiones, localización, etc.
7. ¿Vale la pena pasarse a ASP.NET MVC o sigo usando Webforms?
En mi opinión, probablemente no se trate de decidirse por una u otra tecnología, sino de conocer ambas y utilizar la más apropiada en cada momento. Hay muchos aspectos a tener en cuenta, por citar algunos:
- los conocimientos y experiencia del equipo de desarrollo
- la necesidad de usar controles o sistemas preexistentes
- la madurez del framework
- el futuro de la tecnología
- la importancia de ventajas propias de MVC
- el tipo de sistema que se pretende construir
Vamos a reflexionar sobre cada uno de estos puntos, y la decisión os la dejo a vosotros. ;-)
El equipo de desarrollo
La tecnología de formularios web (Webforms) permite el desarrollo rápido de aplicaciones (RAD) a través de diseñadores visuales con los que es posible componer una página compleja y definir el comportamiento del interfaz a golpe de ratón, puesto que el framework se encarga de realizar parte del trabajo duro, como el mantenimiento del estado entre peticiones, convertir propiedades de controles en código HTML y CSS, o incluso generar scripts que realicen determinadas tareas en cliente. De hecho, siguiendo este modelo es posible crear aplicaciones para Internet sin tener apenas idea de las particularidades inherentes al desarrollo web, lo que permite que muchos programadores procedentes del mundo del escritorio puedan ser productivos muy rápidamente, aunque sea a costa de generar páginas mucho más pesadas y con un código de marcado complejo.
No hay que olvidar que para determinado tipo de aplicaciones, los Webforms son una buena opción, tanto como lo han sido hasta ahora. Por tanto, si el equipo de desarrollo tiene ya experiencia creando aplicaciones con esta tecnología y no poseen grandes conocimientos sobre programación web de más bajo nivel ni experiencia previa trabajando con el patrón MVC, deberíamos pensárnoslo antes de dar el salto a ASP.NET MVC, puesto que la productividad, al menos inicialmente, va a caer.
ASP.NET MVC requiere un conocimiento más profundo del entorno web y sus tecnologías subyacentes, puesto que a la vez que ofrece un control mucho más riguroso sobre los datos que se envían y reciben desde el cliente, exige una mayor responsabilidad por parte del desarrollador, ya que deberá encargarse él mismo de mantener el estado entre peticiones, maquetar las vistas, crear las hojas de estilo apropiadas, e incluso los scripts. Esto, sin embargo, no difiere mucho de la forma de trabajar unos años atrás, y es posible que en el equipo de trabajo haya desarrolladores experimentados que se sientan incluso más cómodos trabajando a este nivel que utilizando abstracciones como las provistas por ASP.NET Webforms.
Controles y módulos reutilizables
Otro aspecto a valorar antes de dar el salto a ASP.NET MVC es que existe una altísima probabilidad de que no podamos utilizar sistemas o componentes que hayamos desarrollado previamente, lo cual redundará en los tiempos de desarrollo y productividad del equipo de trabajo. No nos valdrán los controles de servidor, ni las plantillas de proyectos, ni los generadores de código, y en muchos casos ni siquiera la herencia de editor (que por muy antipatrón que sea seguro que acostumbramos a utilizar).
Probablemente en breve dispondremos de componentes para ASP.NET MVC generados por la propia comunidad de desarrolladores, ya sea en forma de helpers (métodos estáticos de generación de código en cliente), en forma de vistas parciales (por ejemplo en archivos .ASCX) y nos permitan reutilizar código, o incluso como controles de servidor (ya se puede ver algo de eso en el ensamblado MVC Futures, disponible en CodePlex).
Puedes ver un ejemplo de helper en el post “Helper para desplegables enlazados con ASP.NET MVC y jQuery”.
Madurez del framework
ASP.NET MVC es un framework recién salido del horno, por lo cual su adopción implica ciertos riesgos, ya superados por los veteranos Webforms.
En primer lugar, es bastante probable que durante un primer periodo de adopción comiencen a surgir bugs, agujeros de seguridad y otros problemas que podrán hacer tambalear los cimientos de los sistemas que utilicen este marco de trabajo. También es cierto que dada la disponibilidad del código fuente del mismo y su relativa simplicidad frente a los formularios web, los inconvenientes que puedan aparecer podrían ser rápidamente subsanados.
La madurez también se hace patente en la cantidad y calidad de información disponible. ASP.NET MVC, aunque cuenta con una comunidad de desarrolladores bastante entusiasta, son una minoría comparándola con su veterana competencia.
Y lo mismo ocurre con el número ingente de componentes y controles reutilizables disponibles para Webforms. Dado que no son compatibles con el framework MVC, se parte de una situación de clara desventaja frente a éstos, aunque como comentaba anteriormente seguro que con el tiempo este aspecto irá mejorando.
Consideraciones sobre el futuro de la tecnología
Si lo que te preocupa es el futuro de los Webforms, has de saber que Microsoft va a seguir dándoles soporte y mejorándolos, como no podía ser de otra forma. Por tanto, de momento no es necesario que bases tu decisión en esto.
Eso sí, hay quien opina que ASP.NET MVC será el estándar de creación de sistemas web en unos años, por lo que en cualquier caso se trata de una tecnología que no habría que perder de vista…
Beneficios de ASP.NET MVC
Las ventajas de la arquitectura MVC, descritas anteriormente, y las bondades del diseño del framework son un buen aliciente para comenzar a trabajar con ASP.NET MVC. De hecho, deberíamos tener muy en cuenta en qué aspectos nuestros desarrollos van a beneficiarse del uso de esta tecnología y valorar si estas ventajas compensan los inconvenientes que su adopción va a suponer:
- la separación de aspectos impuesta por el patrón MVC obligará a tener un código más limpio y estructurado, independizando totalmente la interfaz de la lógica de navegación y, por supuesto, de la de negocio.
- de la misma forma, esta división facilita el trabajo en equipo, pues permite el avance en paralelo en las distintas capas.
- si entre nuestras prioridades está el asegurar el correcto funcionamiento de nuestros componentes a través de pruebas unitarias, o hemos optado por utilizar una metodología de desarrollo guiado por pruebas (TDD), ASP.NET MVC nos vendrá de perlas. La separación de aspectos citada anteriormente facilita la creación de pruebas específicas para los componentes de cada capa de forma independiente, así como el uso de técnicas avanzadas (mocking, inyección de dependencias…) para que éstas sean lo más completas posible.
- las friendly URLS, o direcciones amigables, es un beneficio directo del uso del framework de Microsoft. Estrictamente hablando no es mérito de la plataforma MVC, sino del juego de clases presentes en el espacio de nombres System.Web.Routing, incluidas en .NET framework 3.5, pero en cualquier caso si optamos por esta tecnología la tendremos “de serie”, con las ventajas que ello conlleva (SEO, REST, claridad en direcciones…).
- al final, el software será mucho más mantenible; el hecho de que los componentes estén separados y bien estructurados simplificará las tareas de mantenimiento.
- el conjunto de convenciones en cuanto a la estructura de proyectos y de nombrado y disposición de elementos facilitará el desarrollo una vez sean asimiladas.
El tipo de sistema
A la hora de plantearse un cambio de este tipo es imprescindible tener en cuenta el tipo de proyecto en el que solemos trabajar. No es lo mismo desarrollar un sitio web colaborativo destinado a un gran número de usuarios, como Facebook o Digg, donde el control fino sobre la entrada y salida es crucial para asegurar aspectos como la escalabilidad, cumplimiento de estándares, o accesibilidad, que crear una aplicación de gestión que utilizarán un grupo relativamente reducido de usuarios desde una intranet corporativa.
Para el primer caso, ASP.NET MVC es una buena opción. La simplicidad de la arquitectura MVC hace que el ciclo de vida de las páginas de este framework sea mucho más sencillo que el de los Webforms, y la ausencia de automatismos y persistencia de estado aligera en gran medida el peso y complejidad de las páginas, lo cual redundará muy positivamente en el rendimiento del sistema. Si además el proyecto requiere o resulta beneficiado por el uso de direcciones URL amigables (por razones de SEO, para presentar un interfaz claro de tipo REST, o cualquier otro motivo), más aún.
Un ejemplo de aplicación real de este tipo es la famosa comunidad StackOverflow.
En cambio, el segundo caso, cuando se trata de crear pesadas aplicaciones de gestión con interfaces de usuario complejos y en las que no es especialmente relevante la calidad del código HTML enviado al cliente, ni el peso de éstas al ser entornos cerrados y controlados, ASP.NET Webforms sigue siendo la opción más razonable. Las facilidades para el desarrollo rápido de aplicaciones (RAD) son mayores utilizando formularios web, aunque sea a cambio de sacrificar aspectos como la separación de código e interfaz, o la facilidad para realización de pruebas unitarias.
8. ¿Puedo convertir mi proyecto ASP.NET Webforms a ASP.NET MVC?
Sí, pero tardarás un buen rato ;-)
Al menos que conozca, no existe ninguna herramienta ni siquiera capaz de intentar realizar tal proeza. Hay que tener en cuenta que el cambio de una a otra tecnología no es una mera traducción como podría ser convertir una aplicación VB.NET a C#; se trata de un nuevo marco de trabajo que afecta sobre todo a la presentación y control de flujo del sistema.
Si tienes unas buenas clases de lógica de negocio, bien aisladas de la tecnología Webforms (como debería ser, por otra parte), probablemente sean los únicos componentes que puedas reutilizar de forma directa, sin grandes cambios. El resto, es decir, todo lo relativo a la interacción con el usuario, habría que convertirlo de forma manual, y por tanto, probablemente habría que pensarse bien si vale la pena hacerlo.
9. ¿Se puede utilizar ASP.NET Ajax con el framework MVC?
Si nos estamos refiriendo a la posibilidad de utilizar controles de servidor Ajax, como el célebre UpdatePanel
o los controles del ASP.NET Ajax Control Toolkit, la respuesta es rotunda: no. De hecho, el modelo MVC no permite el uso de controles de servidor (runat="server"
); bueno, o al menos no lo permite de la forma en que veníamos haciéndolo, pues han dejado de existir aspectos tan fundamentales para ellos como el viewstate o los postbacks.
Ahora bien, si la pregunta la generalizamos como “¿se pueden utilizar librerías Ajax con el framework MVC?” la respuesta es absolutamente. De hecho, ASP.NET MVC se lleva de fábula con librerías de scripting como las incluidas en el framework ASP.NET 3.5, o con la magnífica jQuery. La limpieza de la filosofía MVC hace posible que sea realmente sencillo realizar desde cliente llamadas a los controladores mediante scripting con objeto de obtener datos, actualizar porciones de contenido de la página con el marcado de la vista correspondiente, o, en definitiva, interactuar con el servidor.
En este mismo blog puedes encontrar multitud de ejemplos de integración de jQuery y ASP.NET MVC, que aunque implementados con las previews del framework (¡a ver si un día tengo un rato y los voy actualizando!), pueden ayudarte a entender cómo hacerlo.
Otro aspecto interesante respecto a jQuery es que esta librería entró a formar parte de la plataforma de desarrollo de Microsoft el pasado mes de septiembre, lo que en la práctica aporta varias ventajas: la primera, que jQuery viene incluido de serie en las plantillas de proyectos ASP.NET MVC; la segunda, que Microsoft se ha esforzado por mejorar la integración con Visual Studio de esta librería, facilitando archivos que hacen posible el disfrute de intellisense mientras la utilizamos.
10. ¿Se puede utilizar VB.NET con ASP.NET MVC?
Por supuesto. Aunque la mayoría de código que se encuentra por la red utiliza C#, probablemente porque es el lenguaje en el que ha sido desarrollado y sobre el que se están exponiendo más ejemplos desde las previews más tempranas, cualquier lenguaje .NET podría ser utilizado sin problema para desarrollar aplicaciones sobre este framework.
A nivel de entorno de desarrollo, Visual Basic ofrece el mismo nivel de ayudas y plantillas que C#, pero desconozco si esto es así en otros lenguajes.
11. ¿Puedo usar LINQ desarrollando aplicaciones con ASP.NET MVC framework?
Sí, de hecho se complementan a la perfección.
Aunque LINQ como tal sólo es un mecanismo de consulta integrado en los lenguajes de programación, las tecnologías ORM que lo rodean, como LINQ2SQL o Entity Framework son ideales para implementar los componentes propios del Modelo (la M de “MVC”). En aplicaciones relativamente simples, estas clases podrían generarse con los diseñadores visuales del entorno de desarrollo, o de forma externa con herramientas como SQLMetal, facilitándonos enormemente el trabajo.
Este es un buen momento para comentar que una de las grandes críticas que se están haciendo a la implementación del framework ASP.NET MVC es que parece hacer olvidado la “M”. Si bien el marco de trabajo establece con claridad el alcance y responsabilidades de los controladores y las vistas y dota de herramientas y convenciones específicas a cada una de estas capas, no ocurre lo mismo con el Modelo, que queda totalmente al libre albedrío del desarrollador.
12. ¿Qué tipo de tecnologías puedo utilizar en las vistas?
El objetivo de las vistas es componer el interfaz de usuario y los mecanismos de interacción con el usuario. Lo habitual será utilizar XHTML, CSS y Javascript, aderezado con bloques de código de servidor que se ejecutará en el momento de renderizar la página.
También puedes utilizar la tecnología Ajax para enviar u obtener información desde el servidor, siempre mediante llamadas a acciones definidas en el controlador, que te permitirán crear interfaces más dinámicos y actuales.
Pero sobre todo, nada de utilizar controles de servidor (Label, Button, Dropdowns…). Estos deberán ser sustituidos por sus elementos XHTML equivalentes, lo que implica que perderemos los automatismos provistos por Webforms para el mantenimiento del estado de los controles.
<for each="var name in names"> <test if="name == 'Jose'"> <p>Yo mismo</p> <else/> <p>Amigo: ${name} </test> </for>
Otra posibilidad interesante que aprovecha y demuestra la flexibilidad de la arquitectura de ASP.NET MVC framework, es la utilización de motores de vistas distintos al estándar. Existen multitud de motores ligeros (NHaml, Spark, Brail, NVelocity…), cada uno con su propio lenguaje de marcas y convenciones, que permiten la definición de vistas a partir de plantillas como la que se muestra en el lateral (ejemplo de Spark).
13. ¿Es ASP.NET MVC framework software libre?
He aquí una de las grandes novedades respecto al post que escribí un año atrás. Por aquellos tiempos era inimaginable que esta pregunta pudiera responderse de forma afirmativa, pero… efectivamente, ASP.NET MVC Framework es software libre.
A primeros de abril de 2009 se comenzó a distribuir oficialmente el código fuente de ASP.NET MVC con licencia MS-PL (Microsoft Public License), un modelo de licencia aprobado por la OSI (Open Source Initiative) que permite el uso del software en aplicaciones comerciales y no comerciales.
Publicado en: www.variablenotfound.com
Publicado por José M. Aguilar a las 10:25 p. m.
Etiquetas: asp.net, aspnetmvc, consultas, desarrollo, programación

He actualizado a la versión 1.0 de ASP.NET MVC framework el ejemplo de Helper para crear desplegables enlazados (cascading dropdowns) con jQuery que escribí unos meses atrás.
El contenido del post sigue siendo válido, sólo ha sido necesario retocar algunos detallitos en el código debido a los cambios introducidos en el framework desde la versión Beta.
Descargar proyecto (comprimido en .zip)
Requisitos:
- Visual Studio 2008/Web Developer Express 2008
- Service Pack 1 (VS2008/VWD2008)
- ASP.NET MVC framework 1.0
Publicado en: www.variablenotfound.com.
Tras esperar un poco por aquello del April’s Fool (el equivalente a nuestro Día de los Inocentes ), ya hoy se puede confirmar que el código fuente del framework ASP.NET MVC 1.0 ha sido publicado con licencia MS-PL, lo que en la práctica significa que ha pasado a ser oficialmente software libre.
Aunque el código fuente de la plataforma estaba disponible en CodePlex prácticamente desde que empezaron a publicarse las primeras previews de la plataforma, es ahora cuando, en palabras de Scott Hanselman, ha pasado de ser “source opened” a “open source”.
Muchas de las grandes figuras implicadas en el proyecto han publicado ya en sus respectivos blogs el esperado anuncio, felicitándose por el logro conseguido, una nueva demostración del cambio de rumbo de Microsoft respecto al código abierto.
También Miguel de Icaza, quien por cierto recientemente anunciaba la disponibilidad de Mono 2.4 y MonoDevelop 2.0, ya ha comentado que se trata de una magnífica noticia no sólo para el equipo del Proyecto Mono, sino para toda la comunidad de desarrolladores ASP.NET.
Enlaces (en inglés):
- ASP.NET MVC 1.0 (ScottGu)
- Microsoft ASP.NET MVC 1.0 is now Open Source MS-PL (Hanselman)
- Open Source License For System.Web.Mvc (Haack)
- Rolling a Bubble – ASP.NET MVC is Ms-PL (Connery)
- Microsoft releases ASP.NET under the MS-PL License (Miguel de Icaza)
- Download ASP.NET MVC 1.0
Publicado en: www.variablenotfound.com
Publicado por José M. Aguilar a las 5:42 p. m.
Etiquetas: asp.net, aspnetmvc, microsoft, noticias, software libre

En esta tercera y última entrega de la serie, vamos a centrarnos en otra de las grandes utilidades de las expresiones lambda en .NET framework: la definición de árboles de expresión.
Las lambda como árboles de expresión

Esto es muy diferente al caso anterior, donde hablábamos de las lambda como funciones ejecutables que podían ser referenciadas por delegados e invocadas de forma directa. Entonces las expresiones lambda eran transformadas en tiempo de compilación en código ejecutable (de hecho, en métodos estáticos que pueden ser consultados usando Reflector u otros desensambladores), y por ello podíamos utilizarlas de forma directa.
En el caso de los árboles de expresión, la compilación no genera código ejecutable correspondiente a las instrucciones definidas en la lambda, sino el código para crear y llenar el árbol con dicha expresión. Después, en tiempo de ejecución, será posible recorrer dicho árbol, analizarlo, seriarlo para almacenarlo o moverlo a otras capas, e incluso compilarlo para poder lanzar su ejecución.
Pero paremos aquí un momento... según lo dicho, cuando el compilador se encuentra con una expresión lambda, por ejemplo
x => x * 2
, puede optar por generar una función anónima o por generar el código de llenado del árbol, ¿cómo sabe lo que debe hacer?Pues bien, el compilador elegirá la opción adecuada dependiendo del tipo de la referencia a la expresión lambda. Si se trata de un tipo de delegado como
Func
o Action
, generará código ejecutable y las referencias a la función serán tratados como delegados; si se usa el tipo Expression
, que veremos más adelante, se generará el árbol de expresión y las referencias no se considerarán delegados, sino objetos de este tipo. Por este motivo no podemos utilizar para declarar lambdas variables locales de tipo implícito: el compilador no sabría qué hacer.
var dobla = a => a * 2; // Error: no se puede asignar
// una expresión lambda a una variable
// local de tipo implícito.
Definición de árboles con expresiones lambda
Para definir un árbol de expresión a partir de una lambda debemos utilizar el tipo genéricoExpression<TipoDelegado>
, siendo TipoDelegado
un delegado como Action
o Func
de los descritos en el post anterior. ¿Que esto os parece confuso? Pues esperad a ver el ejemplo... ;-) Expression<Func<int, int, int>> media = (a, b) => (a + b) / 2;
En realidad, aparte de lo difícil de leer que es una declaración de este tipo, la idea es bastante sencilla. Lo que estamos indicando al compilador es que queremos montar un árbol de una expresión de la que conocemos el tipo de los parámetros de entrada y del valor de retorno, datos que indicamos mediante el delegado que utilizamos como argumento genérico de la clase
Expression
, la porción que he marcado de amarillo en el ejemplo anterior. Además, este delegado lo utilizaremos cuando queramos convertir el árbol de expresión en código ejecutable, más adelante veremos cómo.Para que quede claro, ahí van algunos ejemplos más:
// Árbol de expresión de una función que determina
// si el parámetro que le llega es par
Expression<Func<int, bool>> esPar = a => a%2==0;
// Árbol de expresión de una función
// que retorna el máximo de dos números.
Expression<Func<int, int, int>> maximo =
(a, b) => a > b ? a:b;
// Árbol de expresión de una función que
// retorna un string transformado
Expression<Func<string, string>> TrimMays =
a => a.Trim().ToUpper();
// Árbol de expresión de una acción
// sin parámetros que escribe por consola la fecha y hora.
Expression<Action> accion =
() => Console.WriteLine(DateTime.Now);
Fijaos que el tipo de delegado
Action
o Func
, que son los parámetros genéricos de la expresión, son los que definen los tipos de parámetros y retornos de la lambda. En el primer caso, el Func<int, bool>
define que la función recibe un entero y retorna un booleano; en el último caso, ni se envía ni se recibe nada, de ahí que utilicemos un delegado Action
.Un detalle importante, antes de que se me olvide comentarlo. Los árboles de expresión sirven, como su nombre indica, para almacenar expresiones. Esto limita el tipo de construcciones de código que podemos usar en las lambdas que los definen: no está permitido utilizar asignaciones, bloques con llaves { }, ni bucles... debe tratarse de una expresión que pueda representarse en una jerarquía de árbol. Si intentamos saltarnos estas restricciones, el compilador generará un error, aunque el tipo de delegado sea correcto y la función lambda también, como en el siguiente ejemplo:
// Suma los n primeros naturales
Expression<Func<int, int>> expr =
n => {
int t = 0;
for (int i = 1; i <= n; t += i++) ;
return t;
};
// Error CS0834: Una expresión lambda con cuerpo no puede ser
// convertida a árbol de expresión

¿Y cómo hace eso? Muy sencillo. El compilador analiza la expresión, genera la secuencia de instrucciones que compone el árbol, las compila, e introduce el resultado en el ensamblado. El siguiente ejemplo muestra cómo crear un árbol de expresión usando una lambda, y una aproximación al código equivalente que genera el compilador, para que nos podamos hacer una idea del trabajo que nos ahorra esta característica del lenguaje:
// Árbol definido con una lambda:
Expression<Func<int, bool>> esPar = a => a % 2 == 0;
// Y el mismo árbol definido a mano,
// lo que genera el compilador automáticamente:
ParameterExpression param = Expression.Parameter(typeof(int), "a");
ConstantExpression dos = Expression.Constant(2, typeof(int));
ConstantExpression cero = Expression.Constant(0, typeof(int));
BinaryExpression modulo = Expression.Modulo(param, dos);
BinaryExpression comparacion = Expression.Equal(modulo, cero);
Expression<Func<int, bool>> esPar2 =
Expression.Lambda<Func<int, bool>>(comparacion, param);
Uso de los árboles de expresión
Ya sabemos qué son los árboles de expresión y cómo podemos definirlos, pero aún no le hemos visto sentido a su existencia. Pero lo tiene, vaya si lo tiene ;-)En primer lugar, el hecho de poder definir el árbol partiendo de una expresión lambda, además de comodidad a la hora de codificar, nos permite aprovechar el tipado fuerte y la potencia del intellisense para evitar errores. En el ejemplo anterior, las probabilidades de que nos equivoquemos creando el árbol de forma manual son muy superiores a que ocurra si utilizamos la sintaxis lambda.
Segundo, fijaos que en ningún momento se está generando código IL o compilando la expresión representada por la lambda. Estamos creando una estructura en memoria. Esto quiere decir que después podemos procesar esta información como estimemos conveniente; podemos, por ejemplo, analizar su contenido, recorrerlo, seriarlo, o transformarlo, en función de nuestras necesidades. Es ideal, por tanto, cuando tengamos interés en interpretar una expresión para realizar alguna acción con ella.
Vamos a ver ahora varios ejemplos para ilustrar el uso de las lambdas y árboles de expresión en el mundo real.
Linq
En el caso de Linq aplicado a un proveedor externo de datos relacional (por ejemplo, las tecnologías Linq to SQL, o Entity Framework), no tiene interés alguno el código ejecutable asociado a una expresión, sino su estructura, pues al final va a ser traducida al lenguaje o tecnología del almacén de información. Supongamos la siguiente consulta para obtener los productos que comienzan por "S": // Usando una consulta Linq:
var datos = from p in productos
where p.Nombre.StartsWith("S")
select p;
// O su equivalente usando
// operadores de consulta:
var datos = productos.Where(p=>p.Nombre.StartsWith("S"));
La lambda resaltada servirá para crear un árbol de expresión con las condiciones indicadas, pues el método de extensión
Where
aplicado acepta un predicado de tipo Expression
. No se genera ningún método anónimo para la expresión lambda, ni se traduce a IL su contenido: sólo interesa para definir la expresión que será introducida en el árbol. Más adelante, en el momento de extraer realmente la información desde el almacén correspondiente, el componente proveedor de datos recorrerá y analizará la estructura en memoria, generando su equivalente en SQL, que es lo que lanzará al SGBD para obtener los datos.Por cierto, existen en la actualidad una gran cantidad de proveedores de Linq, capaces de transformar los árboles de expresión en consultas a casi cualquier tipo de almacén. Fijaos que la posibilidad de separar la codificación lambda de la interpretación de la expresión hace posible su utilización en una gran variedad de ámbitos.
Cálculo simbólico
Otro ejemplo que ilustra muy bien las posibilidades de los árboles de expresión, de mano del maestro Octavio Hernández. Se trata del artículo Cálculo simbólico en C# 3.0, publicado en la web de El Guille a principios de 2007.A lo largo del artículo se realiza la implementación básica de un sistema de cálculo de derivadas de funciones matemáticas partiendo de un árbol de expresiones. El proceso, que el autor va explicando paso a paso, consiste en analizar el árbol, e ir generando otro árbol con el resultado de la derivación de cada expresión encontrada. A continuación se muestra la porción de código donde se realiza la derivación de una operación de suma, utilizando recursividad para derivar además cada uno de los sumandos:
private static Expression Derive(this Expression e, string paramName)
{
switch (e.NodeType)
{
[...]
// sum rule
case ExpressionType.Add:
{
Expression dleft =
((BinaryExpression) e).Left.Derive(paramName);
Expression dright =
((BinaryExpression) e).Right.Derive(paramName);
return Expression.Add(dleft, dright);
}
[...]
}
}
Al final, fijaos que de nuevo no nos interesa en absoluto la lambda como función anónima ni delegado, sino la estructura de la propia expresión, de forma que podamos recorrerla y transformarla en otra expresión, en este caso la función derivada de la original. El siguiente ejemplo muestra el uso de esta clase:
Expression<Func<double, double>>
funcion = x => x*x; // f(x)=x^2
Expression<Func<double, double>>
derivada = funcion.Derive(); // f'(x)=2*x
Console.WriteLine(derivada); // Muestra la función derivada:
// x => ((x * 1) + (1 * x))
Creedme, vale la pena echarle un vistazo.
ASP.NET MVC
Un último ejemplo, que demuestra la versatilidad del uso de lambdas y árboles de expresión en multitud de escenarios. En el framework ASP.NET MVC, es posible crear enlaces hacia acciones desde dentro de las vistas (páginas .ASPX), que no son sino métodos dentro de unas clases concretas llamadas "controladores". El caso es que para hacer referencia a un método del controlador, pueden utilizarse estas dos vías, de resultado idéntico: // Obtiene un enlace al método "ChangePassword"
// de la clase "AccountController":
Html.ActionLink("Cambiar clave", "ChangePassword", "Account")
// Lo mismo, pero usando un árbol de expresión:
Html.ActionLink<AccountController>
(acc=>acc.ChangePassword(), "Cambiar clave")
Aunque el resultado es el mismo, la segunda usa un árbol de expresión para realizar la referencia al método
ChangePassword
de la clase AccountController
. La implementación del método ActionLink
recorre el árbol generado desde la expresión lambda para obtener el nombre del controlador y del método, por lo que es equivalente a primera fórmula, pero beneficiándose de las ventajas del tipado fuerte y del intellisense en la edición.Los árboles de expresión como código ejecutable
Hasta ahora siempre me he referido a los árboles de expresión como entidades de almacenamiento. De alguna u otra forma, estaba equiparando su utilidad a la cualquier estructura de datos que permitiera guardar y procesar información, lo cual es cierto pero sólo parcialmente.Los árboles de expresión aportan una característica adicional: se pueden convertir en código ejecutable. Es decir, es posible compilar un árbol de expresión en tiempo de ejecución, dando lugar a una función anónima a la que podemos tener acceso, es decir, invocarla, a través de sus delegados.
Veámoslo con un caso concreto. Retomando el ejemplo de obtención de derivadas, sería perfectamente posible obtener el valor de la función derivada en un punto ampliando ligeramente el código visto anteriormente:
Expression<Func<double, double>>
funcion = x => x*x; // f(x)=x^2
Expression<Func<double, double>>
derivada = funcion.Derive(); // f'(x)=2*x
// Compilamos la función derivada
// y obtenemos un delegado a la misma:
Func<double, double> funcDerivada = derivada.Compile();
double result = funcDerivada(6); // Obtenemos el valor de la función
// invocando al delegado con x=6
Console.WriteLine(result); // Muestra "12"
Como se puede observar en el código, la llamada al método
Compile()
devuelve un delegado del tipo Func
indicado en el parámetro genérico de la expresión, que apunta hacia la función anónima creada "al vuelo" a partir de las expresiones contenidas en el árbol. Es decir, desde la definición simbólica contenida en el árbol ¡obtenemos código ejecutable!Aunque espectacular, en realidad no hay nada mágico en esta característica: se trata de ir recorriendo el árbol y emitiendo el código IL correspondiente a cada expresión, que está perfectamente tipificada y definida. En el namespace
System.Linq.Expressions
existe una bonita clase interna llamada ExpressionCompiler
que se dedica exclusivamente a ello, utilizando herramientas suministradas por System.Reflection.Emit
, como los generadores de lenguaje intermedio ILGenerator
.¡Y hasta aquí hemos llegado!
A lo largo de estos tres posts hemos recorrido las principales características y utilidades de las expresiones lambda. Obviamente, han quedado cosas por detrás; no era objetivo de esta serie profundizar demasiado, sino ofrecer una visión suficiente para animar a los desarrolladores a utilizar esta potente característica que nos ofrece C# (y VB.NET).Espero que os haya sido una lectura útil, al menos tanto como me ha resultado a mí su escritura. Ah, y para consultas, sugerencias o puntualizaciones, por aquí me tenéis.
Publicado en: www.variablenotfound.com.
Publicado por José M. Aguilar a las 4:40 p. m.
Etiquetas: árboles de expresión, c#, lambdas, linq, vs2008