Imagen de una planicie como lienzo en blanco para nuestro desarrollo de software a medida

Tutorial de Maven

//Arteco - Tecnologías de la información

  • :)
  • :0
  • :D
  • ;)
  • :]
foto Ramón Arnau

Ramón Arnau

Gerente de Arteco Consulting SL

Entiende cómo funciona Maven y aprende a sacarle el máximo partido al Software de construcción de Proyectos más usado

Maven es la herramienta por excelencia para controlar la construcción y descargar dependencias de cualquier aplicación Java. Desde la compilación hasta la construcción del binario final pasando por los test unitarios. En las siguientes líneas te enseñamos lo que debes saber para convertirte en un profesional de Maven.

Qué es Maven

Maven es una herramienta Open Source desarrollada en Java por la asociación Apache Foundation, un organismo sin ánimo de lucro que publica recursos libres de derechos para asegurar el desarrollo y la innovación en las tecnologías de la información. El objetivo de esta herramienta es facilitar y estandarizar la organización y la construcción de proyectos de software, principalmente para proyectos destinados a la máquina virtual de Java.

Maven simplifica las tareas de compilación y construcción de aplicaciones de software, principalmente usado con lenguajes de programación que tienen como destino ser ejecutadas en la Java Virtual Machine (JVM). Además, incorpora una gestión de dependencias madura con acceso a los repositorios públicos de Maven con más de 16 Millones de librerías disponibles incluyendo todas las versiones de cada una de ellas.

Cómo instalar Maven

A continuación, te explicamos el proceso detallado de cómo proceder para dejarlo bien configurado en tu estación de desarrollo.

Cómo instalar Maven en Ubuntu

De la misma manera que se ha procedido con la instalación del JDK, la herramienta de construcción y de gestión de dependencias de proyecto Java por excelencia Maven se instalará de forma equivalente:

sudo apt install maven

Dando como resultado la instalación de comando mvn que podemos ejecutar desde cualquier directorio. La manera de comprobarlo es solicitando que imprima la versión del mismo con:

mvn -version

Si no ha habido ningún problema durante la instalación podremos ver un contenido similar al siguiente:

Apache Maven 3.6.0
Maven home: /usr/share/maven
Java version: 11.0.6, vendor: Ubuntu, runtime: /usr/lib/jvm/java-11-openjdk-amd64
Default locale: es_ES, platform encoding: UTF-8
OS name: "linux", version: "5.3.0-42-generic", arch: "amd64", family: "unix"

Por último sólo queda instalar el editor de programación de Java que más nos interese.

Descargar Apache Maven para Win/Mac

Maven, al estar programado en Java, éste es portable, por lo que la misma distribución puede usarse en cualquier plataforma que pueda ejecutarse la JVM. Así que únicamente debemos acceder a la página oficial del proyecto Maven y descargar la última versión estable. Ésta se ofrece en varios formatos, aquella que tiene extensión Zip será suficiente en la mayoría de los casos.

Una vez descargada, revise la sección de su plataforma para ver cómo configurarlo correctamente.

Configurar Apache Maven para Windows

La configuración de Maven para Windows es muy sencillo, lo único que debe hacer es descomprimir el archivo Zip descargado del paso anterior y ubicando los ficheros en un directorio. Por ejemplo en el directorio donde se ha almacenado los archivos del JDK: c:\Archivos de Programa\Java\apache-maven-version. Anote la ruta completa porque será necesaria en el siguiente paso.

Una vez descomprimidos los archivos se deberá crear la variable de entorno MAVEN_HOME apuntando a la ruta anterior, base de la instalación. El uso de esta variable permitirá cambiar de una distribución de Maven a otra versión más actualizada sin tener que cambiar todas las referencias a esta difundida por los proyectos.

Por último, añadiremos la ruta de los binarios de Java a la variable de entorno Path para que podamos invocar a maven con el comando mvn desde cualquier directorio:

Path=%MAVEN_HOME%\bin;%Path%

Si la configuración está bien hecha, desde un terminal de comandos podremos invocar a maven a modo de prueba con la siguiente instrucción:

mvn -version

Puede continuar el tutorial por el siguiente paso instalación de un editor Java

Configurar Apache Maven para Mac OSX

La configuración de Maven para Mac OS es tan simple como en Windows, lo único que debe hacer es descomprimir el archivo Zip descargado del paso anterior y ubicando los ficheros en un directorio. Por ejemplo en el directorio donde se ha almacenado los archivos del JDK: /opt/apache-maven-version. Anote la ruta completa porque será necesaria en el siguiente paso.

Una vez descomprimidos los archivos se deberá crear la variable de entorno MAVEN_HOME apuntando a la ruta anterior, base de la instalación. El uso de esta variable permitirá cambiar de una distribución de Maven a otra versión más actualizada sin tener que cambiar todas las referencias a esta difundida por los proyectos.

export $MAVEN_HOME=/opt/apache-maven-<version>

Por último, añadiremos la ruta de los binarios de Java a la variable de entorno Path para que podamos invocar a maven con el comando mvn desde cualquier directorio:

export PATH=$MAVEN_HOME/bin:$PATH

Si la configuración está bien hecha, desde un terminal de comandos podremos invocar a maven a modo de prueba con la siguiente instrucción:

mvn -version

Recuerde que para hacer los cambios permanentes y no tener que invocar a export en cada sesión del terminal, puede añadir ambas sentencias al fichero de inicialización el terminal ubicado en ~/.profile

Puede continuar el tutorial por el siguiente paso instalación de un editor Java

Siguiente paso – Instalar un IDE

Para poder instalar el editor, recuerde que necesita disponer del JDK de Java para poder editar, compilar y ejecutar una aplicación Java. Por otro, lado necesitaremos un buen editor de programación que simplifique las tareas de edición de archivos Java. Y por último conviene incluir el sistema de control de versiones git en nuestro proyecto para no perder ni una coma por error.

Estructura de un proyecto Maven

Maven define que todo proyecto Java, ya sea para construir una librería o para una aplicación, debe tener la siguiente estructura de directorios en el sistema de ficheros:

  • pom.xml: fichero de descripción, ubicado en la raíz del proyecto. En él se indica su nombre, la ubicación que tendrá éste en el repositorio de binarios, las dependencias que necesita para compilar, para ejecutar o para lanzar los test. También se especifica si se hará uso de plugins.
  • src/main/java: directorio en donde se ubicarán los ficheros Java del proyecto que serán compilados y formarán parte del binario resultante. A partir de ese directorio es donde se tendrán en cuenta los paquetes de los ficheros Java. Por ejemplo, el fichero fuente de la clase org.proyecto.Persona se ubicará en src/main/java/org/proyecto/Persona.java.
  • src/main/resources: permite añadir recursos que también se incorporarán dentro del binario resultante, pero que no deben ser compilados. Por ejemplo, los ficheros con extensión .properties, XML o imágenes.
  • src/test/java: directorio para colocar las fuentes Java que únicamente se usarán en la ejecución de los test unitarios. El contenido de este directorio no será empaquetado en el binario final.
  • src/test/resources: necesario si para la ejecución de los test se utilizan otros recursos como ficheros XML o CSV con datos de prueba para verificar los algoritmos. Los ficheros incluidos no serán empaquetados en el fichero final.
  • target/classes: en este directorio se almacenarán las clases Java resultantes de la compilación de las fuentes almacenadas en src/main/java.
  • target/<proyecto.jar>: típicamente los proyectos generarán un binario con el contenido de target/classes más src/main/resources en un único archivo empaquetado con extensión jar. Si el proyecto es una aplicación, éste contendrá además todas las dependencias dentro de él para que se disponga de todo lo necesario a la hora de ejecutar la aplicación, formando un fichero denominado fat-jar.

Prácticamente todos los editores de programación de Java trabajan perfectamente con los proyectos organizados como indica Maven. Se puede considerar que se ha convertido en un estándar de facto. Los editores automáticamente procesan el fichero pom.xml para tener presente las dependencias necesarias y ajustar la configuración del proyecto acorde con lo especificado en el fichero.

Fases de construcción Maven

Una vez definido cómo deben organizarse los ficheros fuente que constituyen un proyecto, el siguiente paso es invocar a Maven para que pueda realizar el proceso de construcción del proyecto. Maven tiene presente las dependencias entre módulos que puede haber, así que si se trata de un proyecto modular, el orden de construcción de los módulos se realizará en el orden correcto que permita satisfacer las dependencias. La construcción de cada módulo individual se realiza de la misma manera que se hace sobre un proyecto simple. Por tanto, ya sea para un módulo o para un proyecto simple, Maven tratará de construir el módulo o proyecto, pasando siempre por las siguientes fases en el orden que se indica:

  1. validate: valida que el proyecto es correcto y que toda la información necesaria está disponible según la especificación de los POMs.
  2. compile: compila el código fuente del proyecto revisando todos los directorios src/main/java, alojando los ficheros .class en target/classes.
  3. test: prueba el código fuente compilado utilizando el marco de prueba unitario indicado en el POM, normalmente JUnit. En esta fase se lanza la ejecución de todos los test. Si el resultado de alguno de ellos no es correcto se interrumpe la construcción.
  4. package: recoge el código compilado y lo empaqueta en su formato distribuible, normalmente como un fichero del tipo <application>.jar.
  5. verify: ejecuta cualquier comprobación de los resultados de las pruebas de integración para garantizar que se cumplan los criterios de calidad.
  6. install: instala el paquete en el repositorio local, para usarlo como dependencia en otros proyectos locales.
  7. deploy: copia el binario construido en el repositorio remoto, para compartirlo con otros desarrolladores y proyectos. Esta fase requiere que se indique la URL del repositorio donde desplegar, así como también las credenciales a usar en caso necesario.
  8. clean: (opcional) Si se invoca manualmente, Maven eliminará todos los recursos generados durante la compilación y el empaquetado, borrando el directorio target.
  9. site: (opcional) produce un informe en HTML acerca del proyecto mostrando la documentación del API de Javadoc y estadísticas según las herramientas de análisis que se hayan configurado.

En la mayoría de las veces será suficiente con lanzar la ejecución de Maven parando en algún momento anterior al deploy si se trabaja localmente. Por ejemplo, en muchas ocasiones bastará con ejecutar package si es una aplicación simple o install si se trata de la actualización de algún módulo usado por otra aplicación. Para indicar hasta qué punto se desea ejecutar la construcción de un proyecto, en la línea de comandos ubicándose el directorio donde está alojado el pom.xml, se invocará a Maven mediante el comando mvn argumentando la fase donde finalizar:

    # update target/classes
    mvn compile

    # install binary into local repository
    mvn install

    # both steps
    mvn compile install

    # clean resources before install
    mvn clean install

Sea cual sea la fase indicada, si pasa por package, Maven dejará disponible el binario localmente ubicado en el directorio target del proyecto o módulo correspondiente.

Gestión de dependencias con Maven

Uno de los mayores beneficios del uso de Maven es la buena gestión de dependencias que realiza la herramienta juntamente con el gran catálogo de librerías que ofrece públicamente. Todas ellas sin ningún coste de uso. Maven viene configurado de serie con unos repositorios públicos donde se despliegan la mayoría de librerías Open Source del ecosistema de Java. Para hacer uso de cualquiera, bastará con indicar una nueva dependencia en el POM del proyecto.

Cuando el proyecto requiere de una dependencia, Maven irá a buscarlo al repositorio local. Si la librería no está alojada ahí, normalmente un fichero con extensión .jar, tratará de descargarlo de Internet buscando en los repositorios públicos. Si lo encuentra remotamente, guardará una copia local para que esté disponible para la siguiente vez. El directorio por defecto del repositorio local suele estar en <home_usuario>/.m2/repository. Aunque puede indicarse una ruta alternativa en el fichero de configuración de Maven <home_usuario>/.m2/settings.xml. Mientras no se indique lo contrario, todas las dependencias de todos los proyectos serán almacenadas en ese directorio. Así que fácilmente pueden acumularse varios Gigas de información a medida que avanza el uso de diferentes librerías y versiones en el conjunto de los proyectos. El usuario es libre de eliminar el contenido de éste, provocando que Maven deba descargar de nuevo las dependencias necesarias.

Las dependencias del proyecto deben ir dentro de la sección de <dependencies>. Debe tenerse en cuenta que éstas pueden tener diferentes ámbitos de uso denominados scopes. El ámbito se indica en el atributo <scope> del XML y permite separar aquellas dependencias que son necesarias para compilar, de otras que serán sólo requeridas durante la ejecución del aplicativo. Maven soporta los siguientes scopes:

  • compile: es el ámbito por defecto en caso de que no se indique ningún otro. Se refiere a las dependencias ordinarias que son necesarias tanto para la compilación como para la ejecución. Por tanto deberán ir acompañando al binario de la aplicación final.
  • provided: son las dependencias que son necesarias para compilación y ejecución al igual que en el ámbito compile, pero con la diferencia de que no hace falta que se añadan al binario de la aplicación. Se considera que estas serán proporcionadas a la aplicación de forma externa a Maven. Este ámbito es útil cuando se despliega una aplicación en un servidor de aplicaciones el cual ya dispone de las librerías necesarias.
  • runtime: hace referencia a aquella que no es necesaria para la compilación, pero sí debe ir acompañando al binario de la aplicación final puesto que la ejecución del programa requerirá alguna funcionalidad de la librería citada.
  • test: reservado para aquellas otras que únicamente son requeridas para realizar las pruebas de test unitarios, por lo que no son necesarias ni para la compilación ni para la ejecución. Por tanto, no acompañarán al binario final.
  • system: a efectos prácticos es similar a compile, con la salvedad de que el fichero JAR es proporcionado manualmente por el programador, indicando la ruta del fichero. No será necesario que Maven lo resuelva como dependencia usando el repositorio local.
  • import: sirve para importar todas las dependencias definidas en otro artefacto de tipo POM. Requiere que las dependencias estén citadas en la sección del XML denominada <dependencyManagement> de este segundo POM.

En la mayoría de las ocasiones sólo será necesario indicar el ámbito de tipo test, puesto que el otro ámbito compile será aplicado por Maven automáticamente en ausencia del dato. Independientemente del ámbito, todas las dependencias deben ir dentro de la sección <dependencies>:

<project ...>
    ...
    <dependencies>
        <dependency>
            <groupId>junit</groupId>
            <artifactId>junit</artifactId>
            <version>4.11</version>
            <scope>test</scope>
        </dependency>
        ...
    </dependencies>
    ...
</project>

La gran variedad de dependencias existentes en Maven hace difícil que el programador pueda recordar qué datos indicar a la hora de incluir una librería. Además, Java está compuesta por una comunidad muy activa de programadores que liberan nuevos recursos y actualizaciones con frecuencia. Todo ello complica la tarea de añadir una librería o artefacto dentro del proyecto. Para facilitar esta tarea existe una página web que ofrece una interfaz de usuario destinada al programador. En ella el usuario puede localizar y copiar la dependencia cómodamente en el POM del proyecto. Esta página hace uso de los mismos repositorios públicos que usa Maven indexando todo su contenido:

La página web ofrece estadísticas de uso de las principales librerías que pueden ser útiles para descubrir otros proyectos a tener presente en futuros desarrollos. A medida que los proyectos crecen, la lista de dependencias también lo hace y por regla de tres, las dependencias transitivas de las librerías incluidas. En ocasiones puede ocurrir que dos dependencias entren en conflicto al usar internamente versiones diferentes de una misma librería. Encontrar y resolver esta situación requiere un trabajo de investigación y de búsquedas por la red no trivial. Una opción que ayuda al diagnóstico es mediante Maven. Se le puede solicitar que muestre información de cómo ha resuelto las dependencias directas e indirectas, indicando qué versión de cada una de ellas se está aplicando.

Para ver el resultado de la resolución de los requerimientos debe ejecutarse el siguiente comando:

mvn dependency:tree

Esta sentencia imprimirá por consola la resolución de dependencias usadas durante la compilación y el empaquetado de la aplicación. Resulta muy útil a la hora de solucionar alguna incompatibilidad entre librerías usadas o comportamientos anómalos en tiempo de ejecución.

Primera aplicación con Maven

La manera más sencilla de realizar una primera aplicación con Maven y Java es invocar al asistente de Maven para que cree un esqueleto de aplicación. Para ello necesitamos hacerle llegar el grupo, y el nombre del project (artifactId) al asistente que puede invocarse desde el terminal.

Por ejemplo si queremos crear un proyecto con el grupo: org.eadp y artifact:my-app ejecutaremos el siguiente comando:

mvn archetype:generate \\
    -DarchetypeArtifactId=maven-archetype-quickstart \\
    -DinteractiveMode=false \\
    -DgroupId=org.eadp \\
    -DartifactId=my-app

La ejecución de un arquetipo de Maven no es más que la aplicación de una plantilla predeterminada que genera un esqueleto de aplicación, creando el contenido dentro del directorio con el mismo nombre que el dado al proyecto a través de la variable artifactId.

El proyecto puede ser importado sin ningún problema desde cualquier editor de programación de Java con soporte para Maven. Pruebe de realizar la construcción del proyecto con mvn package para ver qué sucede.

El generador crea un test inicial como plantilla para que el programador tenga una referencia rápida de cómo crear los tests y poder así aplicar una metodología de desarrollo basada en tests. Puede lanzar la ejecución de los tests desde el terminal de comandos con mvn test

En cualquier caso, le recomendamos que se familiarice con el uso de su IDE de Java preferido que simplificará enormemente las tareas de construcción, depuración, tests y cualquier otra tarea diaria del programador.

Descubre cómo convertirte en un profesional de Maven y simplifica la construcción de tus proyectos Java. Con nuestra guía detallada, aprenderás a instalar y configurar Maven para optimizar tus procesos de desarrollo. ¡Confía en Arteco Consulting, SL, tu aliado en el mundo del desarrollo web! Si lo deseas, puedes dejarnos tus comentarios abajo o escribirnos para compartir tu experiencia o para mejorar este contenido. Saludos!

Mantente Conectado

Newsletter

¡Mantente al día con lo último en tecnología y negocios! Suscríbete a nuestra newsletter y recibe actualizaciones exclusivas directamente en tu correo.

Reunión Online

No dejes pasar la oportunidad de explorar nuevas posibilidades. ¡Agenda una reunión online con nosotros hoy y comencemos a construir juntos el futuro de tu negocio!

  • :D
  • :)
  • ;]
  • :0
  • :}
  • ;)
  • :>

Únete al Equipo

Contamos con una gran cartera de noveles que compaginan su formación académica con la experiencia en Arteco, aprendiendo de la mano de los que están en primera línea. Realizamos un programa intensivo de formación cara a la rápida incorporación en equipos de desarrollo reales.

Persona corriendo por el desierto representando el Team Building de Arteco Consulting
  • :)
  • :0
  • :D
  • ;)
  • :]