lunes, 22 de noviembre de 2010

Programar en tiempos revueltos

Recientemente varios amigos, de diferentes ámbitos, me han hecho la misma pregunta:
“escucha, si yo quisiera dedicarme a la programación, así en serio, como lo haces tú, ¿qué debería estudiar? ¿qué libros me compro?”

Obviamente son gente que, sin ser geeks, más o menos se manejan con la informática.
“os contesto por email” les he dicho a todos. Pero he pensado que mejor lo publico en mi blog, que para eso lo tengo :-), y que lo lean ahí.
Tengo que matizar que cuando mencionan lo de ser programadores, se refieren en concreto a programadores de software de gestión en entornos web. No es que ellos lo mencionaran expresamente, pero entiendo que nadie se plantea de la noche a la mañana “voy a programar motores de renderizado 3D” o "voy a desarrollar un compilador de Java alternativo al de Oracle". Primero porque es complicadísimo y antes que aprender a programar bien tienes que aprender mucho de otras disciplinas (generalmente matemáticas). Y segundo porque no hay tanta demanda.

Hoy día la gran mayoría de los puestos de programador que se solicitan son programadores J2EE o .Net. Programadores de aplicaciones web, vaya. Y se solicitan muchos. Lógico es que mucha gente decida reenfocar su carrera profesional hacia donde brilla el sol. En este caso el mundo del desarrollo web.
El resto de este (Email)Post es bastante subjetivo; no pretendo lo contrario.
Yo veo, en el mundo del desarrollo web, tres divisiones, en lo que lenguajes de programación para el servidor se refiere:
- La primera y más importante, donde juegan las estrellas, es la de Java y .Net. Prácticamente todas las grandes aplicaciones que se inician hoy día, se hacen en Java (J2EE) o en .Net. Me refiero a aplicaciones como las que usan los bancos, las petroleras, las aseguradoras... Bases de datos gigantes, decenas de servidores, con decenas o incluso miles de programadores. Estas aplicaciones son sobre todo aplicaciones de gestión, llenas de CRUDs y de informes.
- La segunda, es la que yo llamo del PHP. Aquí está toda la gente que hace páginas web, más que aplicaciones web. Suele haber mucha página estática, diseños gráficos rompedores, algún panel de control, y puede que algo de gestión. Suelen ser aplicaciones que van todas en un único servidor, a menudo incluso la base de datos, que suele ser MySQL, también está en la misma máquina que el servidor web (que suele ser Apache).
Ya estoy oyendo a los PHPeros decir: “esos es mentira, en PHP hay aplicaciones gigantes, incluso para bancos”. Lo siento amigos PHPeros, si creéis que PHP juega en primera división, es que nunca habéis jugado en primera división.
Y no dudo que se puedan hacer grandes cosas en PHP, pero, por circunstancias que más adelante explico, PHP no es una opción para hacer algo grande de verdad.
En esta división entrarían otros lenguajes que, aunque en su día pudieron llegar a hacer sombra al PHP, hoy se han quedado en el camino, como son Perl, Ruby, Phyton… Son lenguajes que no tienen nada que envidiar a PHP, pero PHP les ha ganado la batalla. Y eso que se podría decir que detrás de Phyton está Google, y que Ruby, con su framework Rails (Ruby On Rails) puso de moda este concepto de On Rails, que viene a significar que las tareas más comunes con las que se encuentran los programadores están simplificadas al máximo y se programa a toda velocidad. Y Perl es un lenguaje que por su especial habilidad para manejar cadenas de texto, es el lenguaje preferido por los administradores de sistemas Unix/Linux.
Y la tercera división, es el resto de lenguajes. Todavía he visto a gente haciendo cosas para la web en C o C++. Incluso lenguajes raros, residuales. No voy a perder el tiempo con esta división.
Alguien estará diciendo… ¿y donde esta Groovy/Grails? Pues, hasta que no lo compró SpringSource (ahora VM Ware), diría que era un lenguaje de segunda o tercera división. Pero ahora diría que es un lenguaje de primera división. Hay que recordar que Groovy es uno de esos lenguajes que en realidad su código luego se traduce a Java, por lo que puede correr perfectamente en un entorno de servidores de aplicaciones Java.
Groovy tiene su framework On Rails, llamado Grails, y que ciertamente es una maravilla. Ríete del PHP. Además Grails (por que al final casi todo el que usa Groovy acaba usando Grails) se integra perfectamente con Spring. Pero incluso con los proyectos más avanzados de Spring como Integration, o Batch. Así que puedes abordar un proyecto gigante con Grails, y donde se te quede corto, pues usas Java puro. Al final se va a instalar todo en un Tomcat o un WebSphere.

Quiero volver a recordar que esta es una opinión y como tal es subjetiva. Si alguien cree que PHP es mejor que Java, que escriba su blog y rabie ahí todo lo que quiera.

¿Por qué estas tres divisiones? No lo tengo claro del todo, pero supongo que es por la cantidad y calidad de herramientas existentes para las diferentes etapas del ciclo de vida de una gran aplicación. En ese sentido, Java es el lenguaje que más librerías y frameworks tiene; el que dispone de los mejores entornos de desarrollo con centenares de plugins; el que más servidores de aplicaciones tiene en su menú. Por no mencionar otras herramientas para la explotación, integración continua, test de estrés, etc. Sin todas herramientas no puedes plantearte programar algo como pueda ser un banco online, por pequeño que sea. Y cuando digo programar un banco online no me refiero solo al front office, que ya sé que hay alguno hecho en PHP. Me refiero a todo lo que conlleva un banco, con sus centenares de módulos. Incluso Java y .Net siguen madurando día a día para poder gestionar mejor las macroaplicaciones que el mundo moderno va necesitando.

Basta de charla, a ver, entonces qué estudio para ser programador de primera ¿java? ¿Me compro un libro de Java?
No quisiera desanimar a mis amigos, pero aprender java sólo es el primer paso de cientos. Porque programar aplicaciones web, abarca muchas disciplinas. Bueno, básicamente se reducen a tres:
Programación, Administración y Diseño. Sí amigo, si quieres ser un buen programador web de primera, tienes que saber algo de administración y algo de diseño. Tienes que saber un poco sobre como funciona un servidor de aplicaciones y un servidor de base de datos por lo menos. Y tienes que saber algo de diseño. No diseño gráfico, sino HTML, hojas de estilo CSS, bien de Javascript, algo de usabilidad y sobre todo saber qué se puede y qué no se puede meter en un interfaz web.

Así que voy a empezar a escupir la retahíla de siglas que recomiendo para cada uno de estos tres pilares. Insisto en que yo soy del mundo Java así que todas las recomendaciones que voy a dar son para convertirse en un Javero de pro. Vamos primero con el más básico, el que menos tienes que saber:

Administración.
Básicamente dos conceptos: Servidor de Aplicaciones y Servidor de Bases de datos. Tienes que ser capaz de instalar estos dos servidores. Y saber por lo menos donde se guardan los logs, y donde los ficheros de configuración. Servidores de aplicaciones Java hay muchos, pero os diría que para empezar, con el Tomcat es suficiente. Si os gusta este tema, podéis avanzar hacia JBoss o GlashFish. Y en cuanto al servidor de base de datos, aquí sí que no hay duda: PostgreSQL. Olvídate de MySQL. Son igual de fácil/difícil de manejar pero Postgres es más potente y robusto. Y punto. ¡Que no! Que MySQL no le hace sombra a Postgres. Pesaos estos del MySQL...
Con el postgres viene un pequeño cliente, el pgAdmin, pero si vas a hacer cosas en serio te recomiendo el Navicat o el EMS Pgsql Manager. No son gratis pero son mucho cómodos para moverse por las tablas, indices, triggers, etc.
Estoy dando por supuesto que al menos sabes lo que es un índice de base de datos. Te perdono que no sepas lo que es un trigger, pero si no sabes lo que es un índice, deja de leer ahora mismo y échate un vistazo a yonkis.com; le sacarás más provecho :-)
No es una casualidad que casi todos los "nombres propios" que he mencionado hasta ahora son open source. Soy un gran fan de open source. No un fanático, pero si un fan. Y como estoy dando por hecho que no vas a pagar por nada mientras te estés formando, todas las recomendaciones que voy a hacer serán open source, salvo que indique lo contrario.

De la administración no os cuento más, dando por supuesto que también se tienen conocimientos avanzados del sistema operativo sobre el que vas a trabajar.

Diseño.
Voy a hablar del pilar del diseño antes que la programación, porque entraña menos complejidad. Vuelvo a aclarar que por diseño no me refiero al diseño gráfico. Por supuesto es un plus dominar el photoshop o ser muy creativo con el CorelDraw, pero aquí nos referimos en esencia al HTML y a las hojas de estilo CSS. Las hojas de estilo son fundamentales. Ya no se usa la etiqueta <table> para definir layouts y plantillas. Ahora son todo <div> con sus correspondientes estilos. Y si quieres hacer interfaces decentes tendrás que usar mucho javascript. ¿Qué pasa con el javascript? pues que es un dolor de lo malo que es... hasta que llegaron Prototype primero y JQuery después. Son frameworks para la manipulación del Ajax, los estilos, el DOM, y hacer todas esas virguerías que antes sólo se podían hacer con flash. Sin duda hoy día JQuery y su hermano JQuery UI (para armonizar el interfaz) son la opción más segura. Además programar con JQuery o incluso extenderlo es muy sencillo. Tanto es así, que ahora, hasta me mola programar en Javascript, cosa que siempre he odiado. Aunque lo cierto, es que yo diría que programo en JQuery más que en Javascript. Creo que no uso ni un sólo método nativo de javascript. Y mejor así.
El javascript tiene un pequeño problema. Y es que como se ejecuta en el navegador, el ordenador que ejecuta ese navegador tiene que ser mínimamente potente. JQuery consume mucho procesador. Así que si te lías a meter efectos y "verbenas" es posible que la página se ejecute muy lenta si tu ordenador tiene más de 5 años.

¿Pero la tendencia no era hacer clientes muy finos y tontos y que sea el servidor el que ejecute toda la lógica?Pues sí. Así es. Podríamos pensar que, por error, nos estamos llevando la lógica (cosas como la validación, la ordenación, agregar o eliminar contenido, etc.) al cliente, o sea, al javascript que se ejecuta en el navegador.
Sin embargo, y esto tenedlo muy presente, dentro de poco, el cliente (navegador) con sus sistema operativo incluido se va a ir al servidor. Los que leísteis mi post anterior ya lo sabéis. Dentro de poco, tu sistema operativo completo se va a ejecutar en un servidor remoto (alguna especie de Terminal Server para los que sepáis lo que es) así que no habrá más problemas con que tu ordenador se quede obsoleto, porque sencillamente, no hay ordenador. Tu "ordenador virtual" siempre será lo suficientemente potente para ejecutar lo que haga falta. Lógicamente, cuanto más pagues más potencia tendrás...

A ver, que me lío. Javascript. Con JQuery. A saco. Y no dejéis de echar un vistazo a los increíbles plugins basados en JQuery como JQgrid, o JTree. Y hay centenares más, algunos muy útiles.
Y del diseño no os cuento más. Si os divierte la fotoedición, siempre viene bien saber crear tus propios iconos, patrones, y cosas así con el Photoshop o con el Gimp que es gratis. También hay programas más específicos para la iconografía, y creación de pequeñas imágenes pensadas para integrarse en un entorno web.

Programación.
Aquí está el turrón. Aquí está el porqué te van a pagar más de 48.000 euros al año -cuando domines todas estas siglas y palabrotas, claro está.
Una vez más doy por hecho que algo de programación sabes. Al menos lo que es un bucle, un condicional, etc. Así que lo primero es aprender la sintaxis y la estructura básica. En un libro de esos gordos de Java te enseñan eso y más. Porque suelen enseñar también programación orientada a objetos. Y si el libro es muy gordo, seguro que también te enseña patrones de diseño. Los patrones son soluciones perfectas a problemas comunes. Conocer los principales patrones de diseño hoy día es fundamental. Y no porque los vayas a usar mucho, sino porque los vas a ver mucho. A menudo te encontrarás implementando interfaces o clases abstractas que no has hecho tú, o que se llaman algo así como nosequeFacade o nosecualTemplate, y es importante que sepas lo que es una Fachada (Facade) o una Plantilla (Template). Para aprender bien patrones de diseño, cuando te manejes más o menos con el Java, te recomiendo el libro Head First Design Patterns.

Cuando ya te manejes con Java y hayas hecho unas cuantas cosas chulas (no basta con el “Hola mundo”) habrá llegado el momento de hacer tu primera página web dinámica. Me refiero a un servlet. Pero antes de meterte a hacer servlet y JSPs, tendrás que leer algún libro sobre J2EE, bueno ahora lo llaman JEE, donde explican todas las librerías que puedas necesitar para hacer aplicaciones web. Aprenderás sobre todo Servlets y JSP. No pierdas demasiado tiempo con los servlets. Y de los JSP… lo más interesante es el JSTL un lenguaje muy básico para meter entre el HTML. Un lenguaje de plantillas que se suele llamar, y se usa sobre todo para hacer bucles y condicionales sin tener que recurrir a meter Java puro entre medias del HTML (que es lo que hace JSP). Hay más lenguajes de plantillas para Java, como Velocity o Framemaker, pero te diría que por ahora con JSTL es suficiente.

Y tendrás que aprender a hacer tus propias Tags, que son atajos para no escribir mucho HTML.
Cuando ya hayas tocado todos los palos del JEE, y sepas hacer conexiones con bases de datos vía JDBC, y sepas serializar objetos a XML y viceversa, tendrás que ponerte con JPA. Las conexiones y accesos a la bases de datos suelen dar mucha guerra. Cuando lo tienes mascado, una configuración simple se hace muy deprisa, pero siempre acabas encontrándote con algún problema de persistencia. Siempre. JPA lo que hace darte una serie de herramientas (funciones y librerías) para que tu propio código genere la base de datos, y cada vez que añadas un objeto nuevo se cree una tabla nueva en tu base de datos. Y si añades un atributo al objeto, pues se añade un campo en la tabla de base de datos. Además te independiza de la base de datos. Da igual cual uses. JPA se encarga de traducir el SQL al de la base de datos subyacente.
Para ser preciso, no es JPA quien lo hace, ya que JPA sólo es un API, un interfaz. Hay que usar una implementación concreta de ese interfaz. Yo recomiendo usar Hibernate, aunque últimamente coge fuerza una alternativa llamada Eclipse-Link. El caso es que no tienes que aprender apenas Hibernate, sino JPA y su lenguaje JPQL que es muy similar al SQL. Cuando le pides algo a la base de datos vía JPA, en realidad lo va a ejecutar Hibernate, que es quien finalmente genera el SQL adaptado a la base de datos que uses. Hibernate soporta las principales bases de datos del mercado, entre ellas claro está, Postgresql que es la que vas a usar.
Si se te ha dado bien, y le has dedicado varias horas al día, puede que sólo hayan pasado 4 meses desde que empezaste. Lógicamente lo único que habrás conseguido es una capa de barniz Java. Currando el día a día es como se consiguen más y más capas de barniz hasta que eres un experto.

Pero no hemos terminado ¿eh? Queda un paso más: Spring. Si vas a hacer aplicaciones web hoy día, usa Spring. Es una macrolibrería o framework con módulos para simplificarte la vida en casi todos los ámbitos de la aplicación: capa de datos, capa de negocio, y capa de presentación.
Mediante la configuración de la aplicación con ficheros XML y/o anotaciones en el código, te evita cientos o miles de líneas de código. Es importante que hayas aprendido bien lo que es un servlet, una llamada Http y todas esas cosas, porque luego, con Spring, no las vas a usar pero vas a saber que está pasando por detrás. Porque si no, te va a parecer que Spring hace magía. Sobre todo en la capa vista.
Spring lo vas a acabar usando y tires por Java puro o por Grails. Pero si Java con Spring te puede llegar a parecer magia, Grails con Spring ni te cuento. Por eso insisto en tener unos conocimientos mínimos sobre como funciona un servidor web, y el protocolo HTTP.

Si no te gusta la capa vista, diseñar interfaces, el HTML, programar en Javascript, no pasa nada. También hay un hueco importante para los programadores que sólo hacen módulos que luego necesitan comunicarse porque generalmente están en distintas máquinas. Para esto suelen usarse los web services. Hasta hace poco se hacía todo con web services XML, y el paradigma SOAP. Pero es tan complicado que mucha gente lo está abandonando a favor de otra forma más sencilla: web services REST. Es mucho más sencillo, y para la mayoría de los casos es suficiente.
Por supuesto Spring tiene módulos tanto para los servicios web XML, como para REST. Ya os digo que cuando empiezas a usar Spring, todo se simplifica. Pero no funciona el atajo de empezar directamente con Spring. Si haces eso, cuando te encuentres un problema de esos raros (que te lo encontrarás seguro) no vas a tener ni idea de qué está pasando, ni siquiera aunque leas con lupa el Stack Trace del error.
Tu kung-fu con la programación será óptimo, cuando, al producirse cualquier error, puedas mirar el Stack Trace (la descripción del error según Java) y saber al instante qué está pasando. Los mensajes de error de Java, a pesar de ser infinitamente más inteligibles que lo que había el siglo pasado, siguen siendo un poco crípticos a veces. Y a menudo te dicen que falla algo con lo que tú no estabas lidiando en ese momento, o que ni sabías que existía. Sin un kung-fu óptimo, pasarás más de la mitad del tiempo resolviendo errores que no sabes por qué se provocan.
Y cuando ya creas que sabes mucho Java entonces te lees el libro Effective Java de Joshua Bloch, el arquitecto Java jefe de Google, y descubrirás que todavía eres un novato.

A todo esto hay que sumarle dos cosas, diría que imprescindibles: UML y el idioma inglés.
UML es un “lenguaje” para analistas. Más bien, por decirlo de forma simple, es una notación para hacer diagramas. Diagramas de estado, diagramas de flujo, diagramas de componentes, diagramas de secuencia, y sobre todo, como programador, diagramas de clases. El UML es muy importante no sólo para preparar lo que vas a hacer y comentarlo con los stakeholders o participantes en el proyecto. También es una muy importante herramienta de documentación. Lo normal es que haces primero todos los diagramas UML y cuando te dan el OK empiezas a programar, siguiendo las pautas de lo que hay en el UML (a veces el UML lo hacen otros). Yo para todo lo relativo al UML uso el Visual Paradigm, que es de lo mejorcito que hay.

El UML es el único gran consenso en lo que a documentación se refiere. Porque aunque mucha gente programa siguiendo muchas pautas (como los patrones de diseño o los patrones de análisis), a la hora de documentar… la norma parece ser que cada cachorro se lama su pito :-). Hay como unos grandes trazos, que te recomiendan que dividas la documentación en visión global, documentación funcional, documentación de análisis, documentación para el programador y documentación para el usuario.
El UML se usa para la documentación de análisis y la documentación para el programador.
Y como decía, la otra cosa imprescindible es que te manejes bien con el inglés. Mantenerte en la cresta de la ola implica lidiar con últimas versiones o incluso versiones beta o alfa. Y como cabe esperar, la documentación de todos estos frameworks o lenguajes está inicialmente en inglés. Y siempre pasa algún tiempo antes de que empieces a encontrar gente que en sus blog en castellano pone ejemplos, traduce partes del manual, o escriben y responden en los foros. No sólo es importante, si no que es casi una condición sin-ecua-non. Pues ir avanzando si sólo lo chapurreas, pero llegará un momento en que notarás como el no saber bien inglés te frena.

Pues ala, a empezar. Si ya sabes inglés, algo de HTML y programas bien en algún otro lenguaje (aunque sea de segunda), en cosa de un año, con una dedicación constante, puedes estar preparado para jugar en primera.

El mundo de la programación hoy día tiene una ventaja: no importa que lleves toda tu vida siendo, qué se yo, embalsamador de moscas, que si te lo tomas en serio, en dos o tres años estudiando lo último de lo último en informática, te puedes hacer con un buen puesto de trabajo bien pagado. Sin embargo es un arma de doble filo, porque si das ese paso, ya no puedes parar. En cuanto dejes de estudiar y mantenerte al día, verás como caché cae empicado. Y si te quedas anclado a una tecnología que se va deprecando, cuando quieras dar el salto verás que tu el mercado laboral no te valora tanto como esperas.

En definitiva, si das el paso de meterte en esta profesión, prepárate para afrontar actualizaciones frecuentes en tu entorno trabajo. Formación continua. En este mundillo, la máxima que tienen los budistas de que lo único constante es el cambio, es especialmente cierta.

domingo, 14 de noviembre de 2010

La evolución de las especies abstractas

Dice un principio del mundo de desarrollo del software, medio en serio medio en coña, que cualquier problema (en el ámbito este del desarrollo) se resuelve con otra capa más de abstracción; con otro wrapper sobre la tecnología existente.

La palabra wrapper, en el contexto de la informática, no tiene una fácil traducción. Envoltorio, lo definen en algunos sitios. Pero no es muy preciso. Ciertamente, a veces una tecnología hace como de envoltorio de otra. La envuelve de modo que tú sólo ves la tecnología más exterior. Como si fueran capas de una cebolla. Sólo ves la capa más externa que es con la que interactúas. A mí me gusta llamarlo capas o niveles de abstracción. Porque cada vez que la humanidad desarrolla una de estas capas, se crean nuevos conceptos que son abstractos, para que no tengas que lidiar con la vieja tecnología que, cosas de la evolución, de repente se nos antoja muy complicada. Es cierto que estos conceptos abstractos nuevos nos simplifican la vida, haciéndonosla más fácil, pero ay de ti como quieras bucear hasta los niveles más interiores; ya te puedes armar de paciencia. Se van creando capas sobre capas con el paso de los años, y, sin darnos cuenta, vamos creando un mundo cada vez más complejo, aunque afortunadamente, se supone que la gran mayoría de nosotros sólo lidiamos con la capa más exterior, y por ende, más simple.
Esto es especialmente cierto en el mundo del desarrollo software. Pero como todos sabemos, cada vez más cosas son software, así que esta teoría se aplica a nuestra vida cotidiana cada día más sin casi sin darnos cuenta.

Sin embargo no deja de preocuparme (más bien fascinarme) los sucesivos niveles de abstracción a medida que avanzan los años. Y no soy el único. Tanto es así, que el “teorema” que menciono al principio tiene también un corolario, con el mismo nivel de seriedad, que dice: Todos, menos el problema de exceso de niveles de abstracción.
Como si de una amenaza, casi un profecía, se tratase, este corolario nos advierte ya hoy de lo peligroso de este problema y nos acerca una de las conclusiones de esta mi reflexión: simplificamos a costa de complicar.

En el mundo de la arquitectura software el concepto de complejidad está muy de moda. Todos los más reconocidos gurús nos sugieren evitarla a toda costa. Y eso es precisamente lo que se está haciendo: la mejor manera de simplificar una pieza de software es hacer un wrapper sobre ésta que sea más sencillo de dominar. He aquí el origen del teorema.

No deja de ser paradójico, que esas piezas de software encargadas de abstraer otra pieza de software, para hacernos la vida más sencilla a los informáticos, son auténticas joyas de la programación; un software realmente complejo, tanto que la mayoría de los programadores/analistas/arquitectos sabemos que no estamos a esa altura. Creo que la empresas o fundaciones encargadas de desarrollar estos wrappers son las que aglutinan a la élite de la programación, y es generalmente ahí donde se forjan los gurús que toman las riendas de la comunidad de los desarrollos durante un tiempo; hasta que se desarrolla un nuevo wrapper sobre lo que ellos desarrollaron y entonces quedan eclipsados (que no desprestigiados, ni mucho menos).

Estas capas de abstracción no se desarrollan de un día para otro. Tardan mucho en pensarse, desarrollarse y sobre todo implantarse. Cada pocos años emerge una, aunque no todas llegan a buen puerto. Esta evolución a base de wrappers me recuerda a un árbol grande cortado, en el que se pueden ver los diferentes anillos concéntricos que nos revelan la edad del árbol. Del mismo modo, desde que existe el software, la edad o el nivel de evolución de la humanidad (y seguramente el de otras vidas extraterrestres :-) ) se mide por cuántas capas de abstracción nos encontramos en el día a día. Podríamos compararlo mejor, con las diferentes y sucesivas capas de sustrato que vemos en la pared de una colina que han cortado transversalmente para hacer una carretera. No hace falta ser geólogo para ver que han pasado muchos años por esa colina. Cada capa de la pared es de un color y un grosor que nos da una pista de lo que pasó en la época de esa capa. Y eso mismo sucede con el software, y es especialmente fácil de ver para los que llevamos una pila de años desarrollando software. Para los que no, voy a intentar explicarlo en el resto de este post.
Hace años, tampoco me voy a remontar a más de 30, no es necesario para entender esto de los niveles de abstracción, cuando desarrollabas un software generalmente lo hacías para un microprocesador concreto. Si tu ordenador tenía un procesador Z80, escribías un código muy críptico para dar instrucciones al procesador; es lo que se llama el lenguaje ensamblador. Una parte del microprocesador convierte ese código a 0 y 1 que es lo que al final entienden todos los microprocesadores.
Claro, tu código sólo servía para los ordenadores que tenían ese procesador. O peor aún, a pesar de que algunos ordenadores de aquella época compartían el procesador Z80, lo que programabas para un Amstrad no valía para un ZX Spectrum.
Esto fue así durante mucho tiempo.

Luego llegaron lenguajes de más alto nivel, como el Basic, Pascal o especialmente el C, que fue el que más triunfó. No he usado más documentación que mi propia memoria para escribir esto, así que no me machaquéis por las imprecisiones, especialmente las imprecisiones en el tiempo. El caso es que allá por los años 80 se empezó a popularizarse en todo el mundo el lenguaje C (en España como siempre, íbamos con algunos años de retraso). Y esta fue para mí la primera gran capa de abstracción. Entonces tú escribías el código de un programa sin pensar en que procesador se iba a ejecutar. De eso se encargaba el compilador, que era un programa al que le decías “conviérteme este código en lenguaje ensamblador para el procesador i8086” “o para el m68000”. El compilador fue el artífice de ese nivel de abstracción. No sólo el lenguaje C hacía que te olvidases de en qué procesador se ejecutaría el programa, sino que además simplificó mucho la vida del programador, ya que éste era mucho más fácil de entender, y por tanto de modificar y mejorar.
Y para mí este fue el primer gran paso hacia la carrera, aun hoy vigente, de intentar simplificar la vida al máximo del desarrollador.

El lenguaje C estuvo mucho tiempo entre nosotros. Tanto fue su éxito que aun hoy mucha gente programa en C. O por lo menos en C++, que no es sino otro nivel de abstracción sobre el lenguaje C. Se trata de la programación orientada a objetos. Los objetos, informáticamente hablando, no son más que una abstracción sobre las tradicionales estructuras de datos de otros lenguajes. Tenemos pues una segunda capa de abstracción que empezó a triunfar en España a principios de los 90. Una década más o menos después del asentamiento del lenguaje C.

Pero entonces (poquitos años antes, para ser preciso) empezó el boom (y la guerra) de los sistemas operativos (Windows, OS/2, Unix, Linux, Mac, etc). El sistema operativo es otro nivel más de abstracción, que se coloca entre el desarrollador y el procesador. A pesar del gran avance que supuso el C y el C++, hacer algo tan sencillo como pintar en pantalla una ventana con los botones de cerrar, minimizar y maximizar, podían ser miles de líneas de código en C.
Así que el sistema operativo proporcionaba (y aún hoy día se hace así) al programador una serie de funciones para que no tuviésemos que preocuparnos por las tareas más habituales como gestionar ficheros, ventanas, sonidos, tipos de letra, procesos en paralelo, controlar el ratón, el teclado, la tarjeta gráfica, etc. Fue un gran avance. Lógicamente, ya no bastaba con saber C++, sino que tenías que conocer las miles de funciones que los sistemas operativos nos brindaban. Hacer un programa que abría una ventana, de pedía que eligieses un fichero de tu disco duro y lo imprimiese, se podía hacer con apenas 20 líneas de código. El sistema operativo ya se encargaba de generar las instrucciones concretas para cada procesador. Insisto, fue un gran avance. Hay que decir que, a su vez, el sistema operativo estaba desarrollado en C. Una vez más, como pasó con los compiladores, se utilizó software, el sistema operativo, para facilitar el desarrollo del software. Y una vez más, se simplificó la vida de mucha gente, no sólo de los programadores. Los sistemas operativos de ventanas fueron un gran progreso para la humanidad en general.


¿Dónde estamos? Ah sí, el sistema operativo. Ahora, al usar las librerías propias del sistema operativo, ya no programabas contra un microprocesador, sino contra un sistema operativo. El código en C++ que pudieras escribir para Windows sólo valía para Windows. No funcionaría en Linux ni en Mac. Cierto es que con ciertas variaciones, especialmente en todo lo relativo a la interfaz de usuario, se podría hacer que un software corriese en diferentes sistemas operativos. Por eso había un Photoshop para Windows y otro para el sistema operativo de los Mac, que entonces creo se llamaba Sistema. Pero aun así, creedme, era un esfuerzo titánico migrar una aplicación de un sistema operativo a otro. Lógicamente, el código para pasar una foto de color a blanco y negro es el mismo, independientemente de para qué sistema operativo se desarrolle. Pero la ventana, los botones y en general todo el interfaz del Photoshop se programan muy diferente si lo haces para Windows que si lo haces para Mac. A veces por algo tan absurdo, como el hecho de que el ratón de los Mac sólo tiene un botón y el de los PC tiene dos.

Tener que pensar para qué sistema operativo desarrollar era frustrante para los comodones programadores. Los que programaban aplicaciones como el Word o el Photoshop lo tenían asumido porque el interfaz cambia tanto de un sistema operativo a otro que no había más remedio. Pero para los que por entonces ya programábamos aplicaciones “servidor” que no tienen ni siquiera ventanas, como pueda ser un servidor Web, ¿por qué pensar en el sistema operativo? Alguien muy listo (y con mucho tiempo libre) pensó en lo que será nuestro siguiente nivel de abstracción.

El invento se llamó Java, y la principal innovación, es que existe una especie de microprocesador virtual que sabe interpretar el código Java. Es lo que se llama la máquina virtual Java, o JVM. Esto ya va sonando más ¿eh? Si es que, a medida que nos movemos hacia las capas más externas, más masa crítica de usuarios encontramos, porque más sencilla de entender, y por tanto más desarrolladores encontramos. Poco tiempo antes habían surgido los lenguajes interpretados como el Perl o el PHP, cuya filosofía es similar a Java, pero en general se ejecutan más lentos.
La magia de Java es que existe una máquina virtual para Windows, otra para Mac, otra para Linux, para Solaris, para AIX, etc. Así, yo hago un programa en Java, que dicho sea de paso es más fácil de entender que el C++, y luego lo ejecuta la máquina virtual. Así que me da igual el sistema operativo. La máquina virtual ejecuta el código java, que lo convierte en instrucciones para el sistema operativo, y este lo convierte en instrucciones para el procesador , pasando por el hecho de que el sistema operativo está programado en C. No es que éste convierta el código Java en código C y éste luego se convierte a ensamblador. No, el sistema operativo lo convierte directamente a código ensamblador, pero el sistema operativo existe porque se desarrolla en C. Desarrollar un sistema operativo en lenguaje ensamblador directamente, sería poco menos que imposible. Sería como construir el Golden Gate sólo con martillos y llaves inglesas manuales.
Los lenguajes de programación interpretados como el Perl o el PHP hacen algo muy similar. Hay intérpretes de Perl y PHP para los principales sistemas operativos. Pera la filosofía de Java era más eficiente. Corrían bien entrados los 90 cuando Java empezó a triunfar. Y tanto fue así, que Microsoft empezó a imitarlo años después. Demasiados para mi gusto. Java había calado muy hondo y había cientos de miles sino millones de programadores desarrollando en Java. Microsoft lanzó su .Net para competir con Java, y aunque hay que reconocer que es una pieza de software muy buena, Java le lleva ventaja.

Una vez más, se usa software, esta vez la JVM de java o la CLI de .Net, para crear otra capa de abstracción. Y aquí ya se abre la caja de Pandora y se lía parda :-). Porque cuando empiezas a programar en Java (voy a referirme en los sucesivo a Java, aunque es igualmente aplicable a .Net) empiezas a usar librerías de código fuente que son wrappers sobre otra librerías y estas a su vez lo son de otras y así hasta... qué sé yo... ¿12 niveles? Sólo voy a citar un ejemplo, que aunque rebasa el nivel de complejidad que quería darle a este Post, puede ser ilustrativo:

El otro día estaba trabajando con un framework, Spring Integration, que hacía una consulta a una base de datos y enviaba lo que leía a una máquina remota. Todo esto lo hacía sin apenas programar 10 líneas de java y unas cuantas líneas XML. Esto hace años habrían sido miles de líneas de código. Esto es posible hoy día porque Spring Integration, en sus archivos de configuración XML, usa un wrapper sobre las librerías Spring Framework, que para el caso concreto del acceso a base de datos usa unas librerías llamadas JPA que son un wrapper sobre otras llamas Hibernate, que a su vez son un wrapper sobre JDBC que a su vez es un wrapper para independizarse de la base de datos, que a su vez es un wrapper sobre el SQL, que a su vez es un wrapper para uniformar la manipulación de las tablas de las bases de datos.

Y si la aplicación es web, prepara otras cuantas capas de abstracción en el navegador, desde las librerías más modernas de Javascript como Jquery UI o ExtJS, hasta el motor de renderizado de HTML de los diferentes navegadores...

Ya el C tenía sus propias librerías que eran wrappers de otras librerías, pero nivel de abstracción que ha adquirido el mundo Java/web asusta. No obstante no pretendo centrarme en los wrappers del código fuente, sino en los wrappers de las tecnologías software. Como la siguiente, siguiendo más o menos la línea de tiempo:
Los lenguajes basados en Java como Groovy o Scala. Hace unos años, no contentos con la simplificación que representa Java, alguien decide que se pueden hacer grandes aplicaciones sin tantas líneas de código Java (y mira que ya vienen siendo pocas) y desarrolla Groovy un lenguaje de programación nuevo, que genera, por decirlo de forma sencilla, código Java, para que sea ejecutado por la JVM.


No se vayan todavía, aun hay más. A medida que las aplicaciones de hoy días son más y más monstruosas, la figura de un administrador de sistemas se hace imperativa, porque estas aplicaciones ya no son como antes que las programa un programador y las instala en un PC y listo. No. La aplicación consta de muchos componentes que se instalan por separado generalmente en distintas máquinas, muchas veces totalmente deslocalizadas. Claro, si tu aplicación necesita de, digamos 20 máquinas cada una con su sistema operativo y su configuración propia, gestionar todas esas máquinas, que no fallen nunca, replicarlas para ofrecer alta disponibilidad, actualizarlas, hacer backups de todas ellas, etc. se convierte en un esfuerzo muy grande y muy complicado. ¿Has dicho complicado? No. Pasa. Nada.
Se mete un nuevo nivel de abstracción y asunto zanjado.
Dicho y hecho. Aquí tenemos la virtualización de los sistemas operativos y con ello la tan de moda Nube, que es otra abstracción más.

Pero vamos por partes, que he soltado ahí la palabrota virtualización muy a la ligera. La virtualización lo que permite es ejecutar varios sistemas operativos sobre un mismo ordenador que ejecuta a su vez otro sistema operativo llamada el sistema operativo Host. En este host, que puede ser, digamos un Windows Server, abres en una ventana un Linux, en otra otro Windows y en otra un MacOS. Y estos tres usando los recursos hardware del sistema Host. Lógicamente no funcionan tan rápido como si se ejecutasen directamente sobre el PC. ¿Para qué hacer eso si el hardware está muy barato hoy día? Se preguntan los más novatos. Para simplificar su administración, la administración de la red de equipos en general. Un sistema operativo que se ejecuta virtualizado en una ventana, tiene toda su información en un fichero gigante del sistema host. Esto significa, que si me llevo ese fichero a un disco duro externo acabo de hacer un backup completo, no sólo de los datos como viene siendo habitual, sino del sistema operativo en sí, con toda su configuración. Si el hardware falla, sólo tengo que llevarme ese fichero a otro PC y en 30 segundos tengo todo funcionando como si no hubiese pasado.
Se pueden hacer cosas como tener 10 PC potentes ejecutando 60 máquinas virtuales, es decir, con 10 sistemas operativos Host, tengo 60 sistemas operativos corriendo. Y el programador no sabe si la máquina donde se ejecutará su código es una máquina virtual o no. Seguramente lo sea. Y si alguna de los 10 PCs host falla y se apaga de golpe no pasa nada, porque lo que se estaba ejecutando en ese PC también se estaba ejecutando simultáneamente en otros dos más. Así que el sistema global que gestiona todas las máquinas virtuales y los host, se encarga de que ahora, en lugar de estar funcionando en una máquina virtual sobre el PC A, estás en un clon de esa máquina virtual en el PC B. Y todo esto de forma transparente para el usuario. El administrador de sistemas recibirá una alerta de que se ha muerto el PC A, se reemplaza, y se reintegra en el sistema y empieza a clonar algunas de las máquinas virtuales por si fallase otro PC.

Esta magia, por si no os parece suficientemente sorprendente, creedme, es algo muy complicado y la gente que desarrolla esta tecnología no son precisamente cuatro becarios.

La virtualización tiene otras muchas ventajas, como la eficiencia energética o la asignación dinámica (sin parar la máquina) de recursos como más memoria o más espacio en disco. En general, insisto, es un gran avance.

Y, como ya me he precipitado en avanzar, existe otro nivel más de abstracción que lo que llaman la nube, el cloud computing. Este concepto de la nube es más un cómo y no un qué. Tú haces un programa y lo hospedas en la nube, de, digamos Google, o Amazon. La nube es siempre la nube de alguna empresa. Y esa nube hace referencia a una cantidad ingente de máquinas Host que ejecutan sistemas operativos virtualizados. Lo que acabamos de ver. Sucede que el programador no se preocupa ni siquiera por el sistema operativo virtualizado. Nosotros sólo subimos nuestro programa a la nube (a una de esas máquinas virtualizadas en realidad) con alguna herramienta generalmente integrada en el entorno de desarrollo. Luego ya ellos, los de la nube, tienen todo configurado para que mi programa se replique por multitud de sistemas operativos virtualizados para que siempre esté online. El concepto de la nube también tiene algo de complejidad pero nada que ver con la que entraña la virtualización de sistemas operativos o la que pueda tener la máquina virtual Java o un sencillo compilador de C.

Ahora mismo, a las puertas del 2011, estamos aquí, con la nube hasta en la sopa. Sin embargo, esto no es más que una parada más. Nadie sabe donde acaba esto. ¿Cuánto llegará a complicarse con el fin de simplificarnos la vida?

Imaginad por un instante, que alguien, no voy a decir ya un romano del siglo I AC, basta con decir del siglo XVIII, viaja en el tiempo hasta hoy, y nos ve usando una hoja de cálculo de Google Docs. Y pide: “explícame como funciona esto, hasta el último detalle”. No podría asimilar tanta complejidad de golpe. Imagino que sería algo similar a cuando los griegos clásicos intentaban entender la vida y el universo sin un microscopio ni un telescopio. No estaban preparados para absorber tanta complejidad y de ahí el origen de la mitología. Que digo yo.

A veces me gusta comparar la evolución del software con la evolución de las especies de Darwin. Imagino el álgebra de Bool, el álgebra binaria, el de los 1's y 0's, sería como la primera bacteria unicelular que apareció. Luego fue mutando y desarrollándose, adquiriendo complejidad hasta ser un pez, luego un anfibio, un reptil, un mamífero, un mono y finalmente el hombre (por no enrollarme demasiado). Si el álgebra de Bool es esa primera bacteria, ¿qué es la nube? ¿los primeros reptiles? ¿un dinosaurio? ¿un ave? ¿tal vez esté tan avanzada la cosa que sea el equivalente a un gorila? El caso es que el software, como la vida, ha ido desarrollándose y adquiriendo una complejidad alucinante.
Aunque para ser honesto, me sigue pareciendo mucho más complicada la vida. Creo que el sistema nervioso de cualquier mamífero tiene muchas más capas de abstracción (desde los átomos hasta el cerebro) que lo que llamamos la nube. Pero tiempo al tiempo.

¿Llegará el software a ser tan complicado como un cerebro humano? ¿Cual es el siguiente paso en esta carrera de abstracciones? Yo la siguiente la veo clara. De hecho, ya está prácticamente aquí. Se trata de eliminar el ordenador. El hardware es un atraso :-). Es decir, que sólo tendríamos una pantalla con una tarjeta de red, un teclado y un ratón, y lo que es todo el almacenamiento, procesador, y resto de hardware está en la nube. Yo encenderé mi pantalla y automáticamente recibiré por red el sistema operativo. Para que esto llegue hemos de pensar que la conexión a internet será tan segura como lo es hoy la corriente eléctrica o el agua. En realidad este concepto lleva varios años entre nosotros y no acabo de entender porqué no triunfa más. Se acabarían los problemas con los discos duros que se estropean, tarjetas gráficas que se quedan obsoletas, procesadores que se recalientan porque el ventilador lleno de polvo ha dejado de girar… Podría ser el fin de la piratería también. Al no tener el control absoluto sobre el sistema operativo sólo podrías instalar software legal. Pero tendrías todo el software del mundo y pagarías sólo por su uso. Por ejemplo, pagaría 10 céntimos de euro por cada minuto que utilice el word, o 50 centimos por cada minuto que use el 3D Studio Max (que consume mucha más memoria y procesador). Pagaríamos sólo por el uso. Dedicaré otro post a este asunto de virtualizar nuestro ordenador de sobremesa.

¿Y el siguiente paso? Aquí ya me adentro en terreno pantanoso porque no veo nada suficientemente claro. Supongo (deseo más bien) que se hará un wrapper sobre el interfaz de entrada salida… Tiene que llegar el día en que nos libremos del ratón el teclado y la pantalla. La pantalla quizá se soluciona con un microproyector, o mejor, con unas gafas que simulan una pantalla de 80 pulgadas (que ya existen hoy día aunque con una calidad un poco penosa). O ya puestos a soñar, pongamos otro wrapper más, para que podamos manejar nuestro ordenador virtual con la mente (que también se están haciendo pinitos en este sentido). Creo voy a parar aquí. No os voy a aburrir con mis paranoias de que en realidad no existimos sino que somos software, o que quizá se pueda virtualizar un cerebro y hacer que éste lleve 7 vidas paralelas como si de sistemas operativos virtuales se tratasen... bueno, ya.


Desde que empecé a pensar este post llevo buscando un ejemplo de un wrapper en el mundo ajeno al software, para ilustrar mejor este concepto y se pudiese entender mejor todo esto que cuento. Sin embargo, esta característica del software no se ve mucho en el mundo analógico. Os digo las dos mejores que se me han ocurrido. 
La primera sería un fondo de inversión. Yo puedo contratar un fondo que invierta en biotecnología en Sudamérica. Y si la biotecnología en Sudamérica va a más yo gano dinero. Pero en realidad el fondo está invirtiendo en empresas concretas de biotecnología en diferentes países de Sudamérica. Podría haber invertido yo directamente en esas empresas, pero tendría que averiguar cuales son, estudiarlas un poco… El fondo de inversión es esa capa de abstracción que me simplifica la vida a la hora de invertir.

El otro ejemplo es un termómetro digital. Seguro que a todos nos costó (a mi aun hoy me cuesta) ver la temperatura que marca el termómetro cuanto te lo quitas después de unos minutos. El funcionamiento de un termómetro clásico no puede ser más simple, sin embargo, su lectura es complicada. Así que alguien aprende a digitalizar lo que el mercurio quiere decir, y te lo muestra en una pantalla que dice 37.5C tienes fiebre. Ahora resulta mucho más fácil leer la temperatura, pero mira qué exageradamente complicado es un termómetro digital frente a uno analógico.

En cualquier caso, generalmente el mundo analógico sólo tiene un nivel de abstracción: pasar al mundo digital, y una vez entra en el terreno digital, el terreno del software, es cuando empieza esa escalada de capas y capas de abstracción. 
Lo mismo pasó con la música y el vídeo, que desde que se convirtieron en digital ambas industrias en general han sufrido tal evolución que no han sido capaces de manejarla con elegancia. Y le diría a los señores de la industria del automóvil que se vayan preparando :-).


En fin, todo esto, para darle la razón a Nicholas Negroponte -el profeta más que gurú- en que el futuro es de los bits y no de los átomos.