En este post intento explicar como construir una aplicación java usando Spring Boot el cual es un proyecto de spring framework que nos permite construir aplicaciones java de forma fácil y rápida al incluir de forma dogmática todas las características y dependencias que una aplicación necesitaría para funcionar en un ambiente de producción (o de desarrollo).

El resultado es que podemos obtener una aplicación java en un ejecutable .jar y correrlo con un simple java -jar o bien un ejecutable .war para deploys mas tradicionales.

Como lo hace? tiene muchas dependencias embebidas que le permite correr de manera idempotente en todos los ambientes donde se despliegue. Si combinamos esto con el poder de docker y/o kubernetes, podríamos encontrarnos en un buen camino hacia una cultura DevOps en la organización donde trabajemos.

Manos al código!

Una de las pocas cosas que vamos a necesitar es, como en todo buen proyecto de java, un gestor de dependencias. Mis favoritos son maven o gradle. Y los respectivos archivos de configuración de dependencias en donde incluiremos spring-boot-starter-web como lo principal para comenzar a trabajar.

Configuración Maven

Simplemente guardamos lo siguiente en un archivo pom.xml en el directorio raíz de nuestro proyecto.

<?xml version="1.0" encoding="UTF-8"?>
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
    <modelVersion>4.0.0</modelVersion>

    <groupId>com.ricardogeek</groupId>
    <artifactId>ejemplo-spring-boot</artifactId>
    <version>1.0.0</version>

    <parent>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-parent</artifactId>
        <version>1.5.10.RELEASE</version>
    </parent>

    <dependencies>
        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-web</artifactId>
        </dependency>
    </dependencies>

    <properties>
        <java.version>1.8</java.version>
    </properties>


    <build>
        <plugins>
            <plugin>
                <groupId>org.springframework.boot</groupId>
                <artifactId>spring-boot-maven-plugin</artifactId>
            </plugin>
        </plugins>
    </build>

</project>

* no se olviden de cambiarle el groupId y artifactId cuando copien este pom.

Configuración Gradle

Simplemente guardamos los siguiente en el archivo build.gradle en el directorio raíz de la aplicación

buildscript {
    repositories {
        mavenCentral()
    }
    dependencies {
        classpath("org.springframework.boot:spring-boot-gradle-plugin:1.5.10.RELEASE")
    }
}

apply plugin: 'java'
apply plugin: 'eclipse'
apply plugin: 'idea'
apply plugin: 'org.springframework.boot'

jar {
    baseName = 'ejemplo-spring-boot'
    version =  '1.0.0'
}

repositories {
    mavenCentral()
}

sourceCompatibility = 1.8
targetCompatibility = 1.8

dependencies {
    compile("org.springframework.boot:spring-boot-starter-web")
    testCompile("junit:junit")
}

* No se olviden de cambiar el baseName en su jar, con el nombre de su proyecto.

Ahora vamos a crear una aplicación web muy simple que saludara al mundo cuando corre.

Creamos los siguientes directorios y archivos en el proyecto:

src/main/java/com/ricardogeek/HolaMundoController.java
src/main/java/com/ricardogeek/Aplicacion.java

En la primera, ponemos el siguiente código:

package com.ricardogeek;

import org.springframework.web.bind.annotation.RestController;
import org.springframework.web.bind.annotation.RequestMapping;

@RestController
public class HolaMundoController {

    @RequestMapping("/")
    public String index() {
        return "Hola Mundo!";
    }

}

Lo primero que notamos es la anotación @RestController que no es mas que una extensión de la anotación @Controller excepto que esta hace que todos los métodos anotados con @RequestMapping tengan, por defecto, un ResponseBody que en este caso no necesariamente mapea a una vista. Al igual que su similar @Controller, @RestController es auto detectado y auto configurado por arte de magia 🙂 (spring es tan fácil!) y no tenemos que preocuparnos de nada mas.

Si ustedes no desean anotar sus clases y usar el tradicional XML pueden hacerlo, lo lindo del xml es que no necesitan re compilar la aplicación cada vez que se cambia la configuración. Basta con reiniciar la aplicación y listo! con anotaciones si se necesita re compilar.

Ahora en la clase Aplicación, ponemos el siguiente código:

package com.ricardogeek;

import java.util.Arrays;

import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.context.ApplicationContext;
import org.springframework.context.annotation.Bean;

@SpringBootApplication
public class Aplicacion {

    public static void main(String[] args) {
        SpringApplication.run(Aplicacion.class, args);
    }

    @Bean
    public CommandLineRunner commandLineRunner(ApplicationContext ctx) {
        return args -> {

            System.out.println("Inspeccionando los beans creados por Spring Boot:");

            String[] beanNames = ctx.getBeanDefinitionNames();
            Arrays.sort(beanNames);
            for (String beanName : beanNames) {
                System.out.println(beanName);
            }

        };
    }

}

Aquí es donde entra en juego la magia de spring-boot, aquí notamos la anotación @SpringBootApplication la cual agrega de forma automática e implicita las siguientes anotaciones :

  • @Configuration Marca esta clase indicando que hay @Bean (s) que deben ser configurados al iniciar la aplicación.
  • @EnableAutoConfiguration Le indica a spring-boot que comience a agregar los @Bean (s) basándose en el classpath, configuraciones y otras propiedades.
  • @ComponentScan El famoso y controversial 🙂 esta pequeña anotación es la que nos libra para bien del xml, marca las clases que lo contienen (implícita o explícitamente) para ser escaneadas al iniciar la aplicación y configurar sus frijoles (@Beans) 🙂
  • @EnableWebMvc esta habilita el viejo y conocido MVC de spring, lo que sucede mas bien es que dentro de nuestra dependencia spring-boot-starter-web se encuentra otra dependencia spring-webmvc lo cual hace que esta anotación sea implícitamente incluida aquí, como todo en spring puede o no usarse 🙂

Finalmente en el método main()  vemos que inicia la aplicación con SpringApplication.run()  y así de fácil amigos! ustedes estarán corriendo una aplicación con todo el poder de java en tan solo unas cuantas lineas (toma esto javascript ?)

El método marcado como @Bean simplemente lista todos los @Beans en la aplicación y es el ejemplo perfecto para se den ustedes cuenta de como todo esta consciente de todo en todo momento, sin necesidad de incluir el classpath en cada archivo (eh! javascript?) basta con tener el ApplicationContext y los @Bean configurados y cargados para acceder a toda la aplicación desde donde sea, sin antipatrones de diseño como ../../../../cosa_fea.js

Ahora para correr la aplicación simplemente ponemos:

Para Gradle:

./gradlew build && java -jar build/libs/ejemplo-spring-boot-1.0.0.jar

Para Maven:

mvn package && java -jar target/ejemplo-spring-boot-1.0.0.jar

En el futuro publicaré mas artículos sobre spring así que manténganse en sintonía.

Manos al código!

 

 

Categorized in:

Tagged in:

, ,