Hoy día es prácticamente imposible encontrarse un proyecto Java que no haga uso de Maven, o de su primo hermano Gradle, ya que no se concibe el manejo y control de un proyecto software sin utilizar una herramienta de gestión que ayude a automatizar tareas y reducir el trabajo repetitivo. Es más, nos hemos acostumbrado tanto a ello que si te pones a desarrollar un proyecto sin hacer uso de éstas herramientas es muy probable que de primeras no sepas cómo llevar a cabo ciertas tareas en principio triviales. Casi podemos decir que Maven se ha convertido en un estándar en el desarrollo Java (aunque también es posible su uso con otros lenguajes) y los beneficios que aporta son considerables, pero si es la primera vez que te enfrentas a él su funcionamiento puede parecer algo arcano y llevarte a preguntar para qué sirve tanto galimatías xml que da más problemas que ayuda.

Supongamos que estás desarrollando un pequeño proyecto Java, una aplicación web basada en Spring que hará uso de una base de datos MariaDB. Quieres manejar mensajes de log, con log4j por ejemplo, y por supuesto, vas a desarrollar tests con JUnit. Para poder utilizar todo este software tienes que buscar los paquetes correspondientes y descargarlos. Además, si alguno de ellos depende de algún otro paquete también tendrás que localizarlo y descargártelo, y así sucesivamente hasta satisfacer todas las dependencias. Una vez que ya tienes todo lo necesario puedes empezar el desarrollo de tu proyecto y en algún momento tendrás que compilar el código fuente escrito y empaquetarlo. En este caso, tienes que crear un .war que pueda desplegarse en el servidor de aplicaciones que estés utilizando. Pero antes de ello estaría bien lanzar los tests que hayas desarrollado y estar seguro que el paquete que has preparado cumple con las validaciones establecidas.

Todo lo anterior es un ejemplo de tareas frecuentes y repetitivas que te encuentras en el desarrollo de un proyecto. Es cierto que el uso de cualquier IDE (Eclipse, Netbeans, …) ayuda en nuestro empeño, por ejemplo a la hora de compilar el código o ejecutar el proyecto, pero se queda corto. Maven te ofrece más potencia y flexibilidad a la hora de automatizar y configurar tu proyecto, porque no sólo puedes manejar lo descrito anteriormente, si no que puedes gestionar muchos más aspectos del mismo. Maven compila el código, lo empaqueta con las características que le especifiquemos, copia o despliega el paquete donde le indiquemos, ejecuta los tests, genera documentación y mucho más. Además, hoy día los principales IDEs integran plugins que permiten su manejo de forma sencilla sin tener que recurrir a la línea de comandos.

Convención sobre Configuración

El funcionamiento de Maven reside en un concepto simple: no dediques tiempo y esfuerzo en la configuración de tus proyectos y, en su lugar, apóyate en convenciones que sean comunes a todos ellos. De esta forma, no tienes que estar reinventando la rueda en cada proyecto y se posibilita la automatización de las tareas. Por ejemplo, Maven asume una estructura de carpetas estándar para cada proyecto: los ficheros de código fuente se ubican en la carpeta src/main/java, los ficheros de recursos (imágenes, ficheros de configuración, etc.) en src/main/resources, el código de los tests en src/test/java, los compilados, paquete generado y resultado de los test en la carpeta target.

Estructura de carpetas en proyecto Maven

En cierto modo, puedes pensar que Maven te fuerza a utilizar una estructura que no es de tu agrado y que pierdes algo de libertad. Pero este planteamiento ofrece muchas más ventajas que posibles inconvenientes. Con esta base prácticamente haces un esfuerzo de coste cero en lo referente a configuración. Tu desarrollas el código y las herramientas que usa Maven, sus plugins, hacen el resto del trabajo por ti. Ellas van a saber dónde buscar el código para compilarlo, dónde dejar el resultado, etc. Aún así, Maven es flexible y es posible personalizar ciertos aspectos de configuración. Pero créeme, apoyarse en la convención ya establecida ahorra una gran cantidad de trabajo. Por otro lado, este enfoque facilita el trabajo cuando te enfrentas a cualquier proyecto que no ha sido desarrollado por ti ya que sabes de antemano cómo está estructurado y no vas a tener que romperte la cabeza y gastar tiempo descubriendo la configuración que surgió de la cabeza de un desarrollador creativo.

El fichero pom.xml

El elemento clave para el funcionamiento de Maven es el fichero pom.xml, cuyo nombre se corresponde con las siglas de Project Object Model. Este fichero se encuentra en la carpeta raíz de todo proyecto basado Maven y contiene todos los aspectos de configuración de dicho proyecto así como las tareas de gestión que deben llevarse a cabo. Un fichero pom puede contener muy pocas líneas y aún así llevar a cabo su cometido. Esto es posible ya que todo fichero pom hereda de un fichero pom global, el denominado Super POM, el cual contiene todos las aspectos de configuración por defecto (como la estructura de carpetas usada para organizar el proyecto descrita anteriormente, por ejemplo). En nuestro pom podemos sobrescribir las propiedades heredades y si no lo hacemos se aplicarán las ya establecidas. Podemos ver el contenido completo del fichero pom que está usando un proyecto ejecutando el siguiente comando:

mvn help:effective-pom

Además, podemos definir nuestros propios pom padre que podremos usar como base para otros proyectos.

Las propiedades que debemos definir obligatoriamente en nuestro pom son las siguientes:

<project>
  <modelVersion>4.0.0</modelVersion>
  <groupId>org.josfranmc</groupId>d>
  <artifactId>prueba</artifactId>
  <version>0.1</version>
</project>

las cuales se corresponden con: el modelo de objeto usado por Maven, el identificador de grupo, el identificador del componente software que vamos a desarrollar (el artefacto) y la versión de dicho componente. A partir de aquí, se puede configurar una gran cantidad de opciones, gestionar las dependencias del proyecto, el comportamiento de los plugins, etc.

Los elementos de configuración de un pom podemos clasificarlos en cuatro categorías:

  • Información general del proyecto: como pueden ser el nombre del proyecto, su url, la organización que lo desarrolla, datos de los desarrolladores, licencia usada, etc.

  • Configuración de compilación: permite personalizar el comportamiento de la compilación a llevar a cabo, la ubicación de ficheros fuente y de pruebas, plugins utilizados, etc.

  • Entorno de construcción: personaliza la configuración de compilación para entornos específicos, típicamente se diferencia entre entorno de desarollo y de producción.

  • Relaciones pom: establece las relaciones con otros proyectos pom, tanto la herencia respecto al pom padre como el uso de submódulos.

En próximas entradas iremos viendo con más detalle los diferentes elementos que conforman el ecosistema Maven y aprenderemos a trabajar con ellos.