Deshabilite toda la configuración automática relacionada con la base de datos en Spring Boot

115

Estoy usando Spring Boot para desarrollar dos aplicaciones, una sirve como servidor y la otra es una aplicación cliente. Sin embargo, ambos son la misma aplicación que funcionan de manera diferente según el perfil activo. Estoy usando la función de configuración automática de Spring Boot para configurar mis aplicaciones.

Quiero deshabilitar toda la configuración automática relacionada con la base de datos en la aplicación cliente, ya que no requerirá conexión a la base de datos. La aplicación no debe intentar establecer una conexión con la base de datos, ni intentar utilizar ninguna de las funciones de Spring Data o Hibernate. La habilitación o deshabilitación de la configuración automática de la base de datos debe estar condicionada y basada en el perfil activo de la aplicación.

¿Puedo lograr esto creando dos archivos application.properties diferentes para los perfiles respectivos?

Intenté agregar esto a mi archivo de propiedades,

spring.autoconfigure.exclude=org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration\
  org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration\
org.springframework.boot.autoconfigure.jdbc.DataSourceTransactionManagerAutoConfiguration\
  org.springframework.boot.autoconfigure.data.web.SpringDataWebAutoConfiguration

Sin embargo, la aplicación aún intenta conectarse a la base de datos al inicio. ¿Son esas exclusiones suficientes para cumplir con mi requisito?

Yuva
fuente
Esto podría ayudar.
Rahul Sharma
¿Puede revelar su código / configuración?
luboskrnac
2
También puede usar sus perfiles de herramientas de compilación y agregar las dependencias relacionadas con los datos solo en uno de sus perfiles. Si empaqueta su aplicación con el otro perfil, ya que no tiene los paquetes de inicio requeridos presentes en la ruta de clase, no se configurará automáticamente
Ali Dehghani

Respuestas:

99

La forma en que haría algo similar es:

@Configuration
@EnableAutoConfiguration(exclude = {DataSourceAutoConfiguration.class, DataSourceTransactionManagerAutoConfiguration.class, HibernateJpaAutoConfiguration.class})
@Profile ("client_app_profile_name")
public class ClientAppConfiguration {
    //it can be left blank
}

Escriba uno similar para la aplicación del servidor (sin exclusiones).

El último paso es deshabilitar la configuración automática de la clase principal de arranque de primavera:

@SpringBootApplication
public class SomeApplication extends SpringBootServletInitializer {

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

    protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
        return application.sources(SomeApplication.class);
    }
}

Cambiar: @SpringBootApplicationen:

@Configuration 
@ComponentScan

Esto debería hacer el trabajo. Ahora, las dependencias que excluí en el ejemplo pueden estar incompletas. Fueron suficientes para mí, pero no estoy seguro de si todo es para deshabilitar completamente las bibliotecas relacionadas con la base de datos. Consulte la lista a continuación para asegurarse:

http://docs.spring.io/spring-boot/docs/current-SNAPSHOT/reference/htmlsingle/#auto-configuration-classes

Espero que ayude

patrykos91
fuente
5
@SpringBootApplicationTiene una excludepropiedad, no necesita ClientAppConfiguration.
Abhijit Sarkar
¿Puede hacer eso excluir condicional basado en el perfil activo sin usar ClientAppConfiguration?
patrykos91
1
Si. Excluiría en el @SpringBootApplication, y luego en el paquete específico, crearía una @Configurationclase que hace una @Importde las clases relevantes y depende de @Profileo @Conditional. De esa manera, puede probar cada capa de la aplicación sin que la configuración automática se filtre por toda la aplicación. ¿Quieres probar DB? Simplemente escanee el paquete de la base de datos, configure una base de datos simulada y listo.
Abhijit Sarkar
87

Para deshabilitar toda la autoconfiguración relacionada con la base de datos y salir de:

No se puede determinar la clase de controlador de base de datos incorporada para el tipo de base de datos NINGUNO

1. Usando anotación:

@SpringBootApplication
@EnableAutoConfiguration(exclude = {DataSourceAutoConfiguration.class, DataSourceTransactionManagerAutoConfiguration.class, HibernateJpaAutoConfiguration.class})
public class Application {

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

2. Usando Application.properties:

spring.autoconfigure.exclude=org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration, org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration
Jorge López
fuente
el uso de Application.properties con Spring Boot 2+ es preferible a la anotación.
Gustavo Rodrigues
@GustavoRodrigues ¿puede compartir alguna documentación para respaldar su declaración? ¡Gracias!
Betlista
27

Parece que olvidaste la coma para separar las clases. Entonces, según su configuración, funcionará lo siguiente:

spring.autoconfigure.exclude=org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration,\
    org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration,\
    org.springframework.boot.autoconfigure.jdbc.DataSourceTransactionManagerAutoConfiguration,\
    org.springframework.boot.autoconfigure.data.web.SpringDataWebAutoConfiguration

Alternativamente, también puede definirlo de la siguiente manera:

spring.autoconfigure.exclude[0]=org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration
spring.autoconfigure.exclude[1]=org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration
spring.autoconfigure.exclude[2]=org.springframework.boot.autoconfigure.jdbc.DataSourceTransactionManagerAutoConfiguration
spring.autoconfigure.exclude[3]=org.springframework.boot.autoconfigure.data.web.SpringDataWebAutoConfiguration
Julien mayo
fuente
17

Existe una forma de excluir clases específicas de configuración automática mediante la @SpringBootApplicationanotación.

@Import(MyPersistenceConfiguration.class)
@SpringBootApplication(exclude = {
        DataSourceAutoConfiguration.class, 
        DataSourceTransactionManagerAutoConfiguration.class,
        HibernateJpaAutoConfiguration.class})
public class MySpringBootApplication {         
    public static void main(String[] args) {
        SpringApplication.run(MySpringBootApplication.class, args);
    }
}

@SpringBootApplication#excludeatributo es un alias para @EnableAutoConfiguration#excludeatributo y lo encuentro bastante útil y útil.
Agregué @Import(MyPersistenceConfiguration.class)al ejemplo para demostrar cómo puede aplicar la configuración de su base de datos personalizada.

naXa
fuente
2
¡Gracias! Esta es la respuesta más moderna. Vinculado a él aquí: konstructcomputers.blogspot.com/2018/10/…
Joshua Davis
9

La salida para mí fue agregar

@EnableAutoConfiguration(exclude = {DataSourceAutoConfiguration.class, DataSourceTransactionManagerAutoConfiguration.class, HibernateJpaAutoConfiguration.class})

anotación a la clase que ejecuta Spring boot (marcada con `@SpringBootApplication).

Finalmente, se ve así:

@SpringBootApplication
@EnableAutoConfiguration(exclude = {DataSourceAutoConfiguration.class, DataSourceTransactionManagerAutoConfiguration.class, HibernateJpaAutoConfiguration.class})
public class Application{

    public static void main(String[] args) {
        SpringApplication.run(Application.class, args);
    }
 }
Ryzhman
fuente
7

Otra forma de controlarlo a través de Perfiles es esta:

// note: no @SpringApplication annotation here
@Import(DatabaseConfig.class)
public class Application {

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

@Configuration
@Import({DatabaseConfig.WithDB.class, DatabaseConfig.WithoutDB.class})
public class DatabaseConfig {

    @Profile("!db")
    @EnableAutoConfiguration(
            exclude = {DataSourceAutoConfiguration.class,   DataSourceTransactionManagerAutoConfiguration.class,
                HibernateJpaAutoConfiguration.class})
    static class WithoutDB {

    }

    @Profile("db")
    @EnableAutoConfiguration
    static class WithDB {

    }
}
Puñal
fuente
¿Puede decirme cómo poner un registrador dentro de la clase WithoutDB y WithDB para que cuando inicie la aplicación imprima algún mensaje? Gracias
ankur pramanik
2

Tuve el mismo problema aquí, resuelto así:

Simplemente agregue otro application-{yourprofile}.ymldonde "su perfil" podría ser "cliente".

En mi caso, solo quería eliminar Redis en un perfil de desarrollador, así que agregué un application-dev.ymljunto al principal application.ymle hizo el trabajo.

En este archivo pongo:

spring.autoconfigure.exclude: org.springframework.boot.autoconfigure.data.redis.RedisAutoConfiguration,org.springframework.boot.autoconfigure.data.redis.RedisRepositoriesAutoConfiguration

esto también debería funcionar con archivos de propiedades.

Me gusta el hecho de que no es necesario cambiar el código de la aplicación para hacer eso.

Sylvain
fuente
0

Recibí este error incluso si hice todas las soluciones mencionadas anteriormente.

 by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'dataSource' defined in class path resource [org/springframework/boot/autoconfigure/jdbc/DataSourceConfig ...

En algún momento, cuando busqué el POM, hubo esta dependencia en él

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

Y la clase Pojo tuvo las siguientes importaciones

import javax.persistence.Entity; import javax.persistence.GeneratedValue; import javax.persistence.Id;

Lo que muestra claramente que la aplicación esperaba una fuente de datos.

Lo que hice fue eliminar la dependencia de JPA de pom y reemplacé las importaciones de pojo con lo siguiente una vez

import org.springframework.data.annotation.Id; import org.springframework.data.mongodb.core.mapping.Document;

Finalmente obtuve una compilación EXITOSA. Compruébalo, es posible que te hayas encontrado con el mismo problema

Tadele Ayelegn
fuente
Esta no es una solución al problema discutido. El problema no se trata de eliminar el soporte JPA de la aplicación por completo, sino de habilitarlo / deshabilitarlo en función de una condición (como un perfil de Spring), sin cambiar el código o la configuración del proyecto Maven. Recibía el error relacionado con la fuente de datos porque, aparentemente, se olvidó de definir y activar el perfil Spring que cargaría la configuración "sin fuente de datos" en lugar de cargar las clases relacionadas con DS / JPA. Las bibliotecas JPA aún deberían permanecer en la distribución.
cvnew
1
No creo que hayas leído mi publicación por completo. En la última línea, sugiero que puede ser un problema similar, pero no digo que esa sea la respuesta
Tadele Ayelegn
0

Agrego myApp.java, después de @SpringBootApplication

@EnableAutoConfiguration (exclude = {DataSourceAutoConfiguration.class, DataSourceTransactionManagerAutoConfiguration.class, HibernateJpaAutoConfiguration.class})

Y cambiado

@SpringBootApplication => @Configuration

Entonces, tengo esto en mi clase principal (myApp.java)

package br.com.company.project.app;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.jdbc.DataSourceAutoConfiguration;
import org.springframework.boot.autoconfigure.jdbc.DataSourceTransactionManagerAutoConfiguration;
import org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration;
import org.springframework.context.annotation.Configuration;

@Configuration
@EnableAutoConfiguration(exclude = {DataSourceAutoConfiguration.class, DataSourceTransactionManagerAutoConfiguration.class, HibernateJpaAutoConfiguration.class})
public class SomeApplication {

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

}

¡Y trabaja para mí! =)

Cássia Chagas
fuente