Carga inicial en Spring Boot

carga-inicial-datos-spring-boot

carga-inicial-datos-spring-boot


Una de las necesidades que nos encontramos muchas veces es popular nuestra base de datos con algún Script inicial. Por ese motivo vamos a mostrar como realizar carga inicial en Spring Boot al arrancar la aplicación.

Aunque existen algunas herramientas para mantener un histórico y hacer carga inicial de datos, como puede ser flyway, en esta entrada nos vamos a centrar en las facilidades que nos da Spring Boot para poder crear una carga inicial de datos sql y creación de tablas en una base de datos. Para ello nos apoyaremos en Spring Data para realizar las conexiones con nuestra base de datos, poder realizar la persistencia y creación automática de las tablas.

Además si queremos eliminar la automatización y realizar de manera manual carga de datos y creación de tablas veremos como usar dos tipos de ficheros, data.sql y schema.sql.

Uso de Schema.sql

Aunque cuando trabajamos con Spring Data podemos delegar en el framework la creación de nuestras tablas a través de la anotación @Entity, si queremos evitar esa automatización podemos hacer uso de un fichero que se llame schema.sql. Este fichero deberá ir dentro de la carpeta resources y será cargado al arrancar la aplicación.

En el caso en el que usemos esta opción habrá que desactivar la creación automática de las tablas en nuestro fichero de propiedades:

spring.jpa.hibernate.ddl-auto=none
CREATE TABLE car (
    id   INTEGER      NOT NULL AUTO_INCREMENT,
    brand VARCHAR(128) NOT NULL,
    model VARCHAR(128) NOT NULL,
    color VARCHAR(128),
    PRIMARY KEY (id)
);

Uso de data.sql para la carga inicial en Spring Boot

Una vez que se ha creado la tabla, necesitaremos cargar datos en nuestra base de datos, para ello vamos a hacer uso de data.sql. Este fichero deberá estar dentro de la carpeta resources.

INSERT INTO car VALUES (1,'Ford', 'yellow', 'Mustang');

Creación de la base de datos con Hibernate

Spring a través de sus propiedades y de la dependencia de Spring Data:

        <dependency>
            <groupId>org.springframework.boot</groupId>
            <artifactId>spring-boot-starter-data-jpa</artifactId>
        </dependency>

nos va a proporciona una propiedad que Hibernate usará para la generación de DDL, spring.jpa.hibernate.ddl-auto.

Esta propiedad podrá tener cinco valores:

  • create – Con esta propiedad Hibernate hará primer un Drop, para a continuación crear las nuevas tablas o tabla.
  • update – En este caso Hibernate nunca borrará las tablas o las columnas, simplemente actualizará el schema si hay algún cambio.
  • create-drop – Esta opción es la típica que usaremos en test, lo que hará será crear al principio y borrar la base de datos una vez hemos realizado todas las operaciones.
  • validate – En Esta opción se valida y tablas y columnas existen, en el caso en el que no exisan se lanza una excepción.
  • none – Con esta opción desactivamos la generación DDL, por ejemplo si queremos, crear a manos las tablas.

Spring Boot elegirá un valor por defecto en función de si la base de datos esta embebida con create-drop o none sino lo está.

Anotación @Sql

Cuando creamos nuestros test tendremos una batería de datos de prueba los cuales vamos a querer cargar o crear sus tablas, para esos casos haremos uso de @Sql. Esta anotación la podemos usar a nivel de clase o de método.

Carga inicial de datos con @sql | carga inicial en Spring Boo
Carga inicial de datos con @sql

@SpringBootTest
@Sql({"/schema_test.sql","/test_cars.sql"})
public class CarServiceIntegrationTest {

    @Autowired
    private CarRepository carRepository;

    @Test
    public void testFindAll() {
        assertEquals(1, carRepository.findAll().size());
    }
}

Existen diferentes atributos que podemos usar con la anotación @SQL que nos facilitará el trabajo sobre todo en nuestra parte de testing:

  • config – configuración local para los scripts. Este atributo irá acompañado de una anotación propia @SqlConfig, que indicará si aplica la configuración de manera local.
  • executionPhase – establecemos cuando ejecutar los scripts, antes o después del método: BEFORE_TEST_METHOD or AFTER_TEST_METHOD
  • statements – este atributo nos permitirá ejecutar sentencias SQL.
  • scripts – el path del script SQL.

O como hemos indicado lo podemos establecer a nivel de método:

    @Test
    @Sql({"/schema_test.sql","/test_cars.sql"})
    public void testFindAll() {
        assertEquals(1, carRepository.findAll().size());
    }

Como hemos visto uno de los atributos que podemos aplicar a nuestra anotación @SQL es config, el cual nos ayudará para nuestra configuración en local, vamos verlo con un ejemplo.

@Test
@Sql(scripts = {"/test_cars.sql"}, 
  config = @SqlConfig(encoding = "utf-8", transactionMode = TransactionMode.ISOLATED))
public void testLoadDataForTestCase() {
    assertEquals(1, carRepository.findAll().size());
}

Como podemos ver en el ejemplo anterior @SqlConfig nos va a ayudar establecer una serie de propiedades para ese test en concreto, como por ejemplo el encoding y el modo de transacción.

Conclusión

En este artículo sobre la Carga inicial en Spring Boot, hemos visto diferentes maneras de cargar datos de manera inicial haciendo uso de los ficheros schema.sql y data.sql y de la anotación @Sql.

Tal y como hemos comentado al principio existen herramientas mucho más avanzadas y óptimas para realizar este tipo de carga de datos como Flyway.

Si quieres echar un vistazo al código y a un test funcionando puedes echar un vistazo en nuestro github.


Deja una respuesta

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *