为什么添加@EnableAutoConfiguration
到以下spring-boot应用程序会导致它无法创建entityManagerFactory
?如果我删除@EnableAutoConfiguration
一切正常.任何人都可以阐明这种行为吗?
package test.builder; import javax.sql.DataSource; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.beans.factory.annotation.Value; import org.springframework.boot.CommandLineRunner; import org.springframework.boot.SpringApplication; import org.springframework.context.annotation.AnnotationConfigApplicationContext; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.PropertySource; import org.springframework.context.support.AbstractApplicationContext; import org.springframework.context.support.PropertySourcesPlaceholderConfigurer; import org.springframework.data.jpa.repository.config.EnableJpaRepositories; import org.springframework.orm.jpa.JpaTransactionManager; import org.springframework.orm.jpa.JpaVendorAdapter; import org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean; import org.springframework.orm.jpa.vendor.Database; import org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter; import org.springframework.transaction.PlatformTransactionManager; import test.builder.jpa.entity.Builder; import test.builder.jpa.repository.BuilderRepository; @Configuration // @EnableAutoConfiguration @EnableJpaRepositories("test.builder") @PropertySource("classpath:application.properties") public class BootApp implements CommandLineRunner { private static Logger logger = LoggerFactory.getLogger(BootApp.class); @Value("${spring.datasource.driverClassName}") private String databaseDriverClassName; @Value("${spring.datasource.url}") private String datasourceUrl; @Value("${spring.datasource.username}") private String databaseUsername; @Value("${spring.datasource.password}") private String databasePassword; @Bean public static PropertySourcesPlaceholderConfigurer placeHolderConfigurer() { return new PropertySourcesPlaceholderConfigurer(); } @Bean public DataSource dataSource() { org.apache.tomcat.jdbc.pool.DataSource ds = new org.apache.tomcat.jdbc.pool.DataSource(); ds.setDriverClassName(databaseDriverClassName); ds.setUrl(datasourceUrl); ds.setUsername(databaseUsername); ds.setPassword(databasePassword); return ds; } @Bean public LocalContainerEntityManagerFactoryBean entityManagerFactory(DataSource dataSource, JpaVendorAdapter jpaVendorAdapter) { LocalContainerEntityManagerFactoryBean lef = new LocalContainerEntityManagerFactoryBean(); lef.setDataSource(dataSource); lef.setJpaVendorAdapter(jpaVendorAdapter); lef.setPackagesToScan("test.builder"); return lef; } @Bean public JpaVendorAdapter jpaVendorAdapter() { HibernateJpaVendorAdapter hibernateJpaVendorAdapter = new HibernateJpaVendorAdapter(); hibernateJpaVendorAdapter.setShowSql(true); hibernateJpaVendorAdapter.setGenerateDdl(false); hibernateJpaVendorAdapter.setDatabase(Database.SQL_SERVER); return hibernateJpaVendorAdapter; } @Bean public PlatformTransactionManager transactionManager() { return new JpaTransactionManager(); } @Override public void run(String... args) { AbstractApplicationContext context = new AnnotationConfigApplicationContext(BootApp.class); BuilderRepository repository = context.getBean(BuilderRepository.class); Builder builder = repository.findOne(10); logger.info("Retrieved ", builder.toString()); context.close(); } public static void main(String[] args) { SpringApplication.run(BootApp.class, args); } }
潜在的错误是
Unable to find JPA packages to scan, please define a @ComponentScan annotation or disable JpaAutoConfiguration
完整输出(包括堆栈跟踪)是 -
14:53:50,842 |-INFO in ch.qos.logback.classic.LoggerContext[default] - Could NOT find resource [logback.groovy] 14:53:50,843 |-INFO in ch.qos.logback.classic.LoggerContext[default] - Could NOT find resource [logback-test.xml] 14:53:50,991 |-INFO in ch.qos.logback.core.joran.action.AppenderAction - About to instantiate appender of type [ch.qos.logback.core.ConsoleAppender] 14:53:50,997 |-INFO in ch.qos.logback.core.joran.action.AppenderAction - Naming appender as [STDOUT] 14:53:51,017 |-INFO in ch.qos.logback.core.joran.action.NestedComplexPropertyIA - Assuming default type [ch.qos.logback.classic.encoder.PatternLayoutEncoder] for [encoder] property 14:53:51,114 |-INFO in ch.qos.logback.classic.joran.action.RootLoggerAction - Setting level of ROOT logger to INFO 14:53:51,114 |-INFO in ch.qos.logback.core.joran.action.AppenderRefAction - Attaching appender named [STDOUT] to Logger[ROOT] 14:53:51,115 |-INFO in ch.qos.logback.classic.joran.action.ConfigurationAction - End of configuration. 14:53:51,117 |-INFO in ch.qos.logback.classic.joran.JoranConfigurator@5ece2187 - Registering current configuration as safe fallback point . ____ _ __ _ _ /\\ / ___'_ __ _ _(_)_ __ __ _ \ \ \ \ ( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \ \\/ ___)| |_)| | | | | || (_| | ) ) ) ) ' |____| .__|_| |_|_| |_\__, | / / / / =========|_|==============|___/=/_/_/_/ :: Spring Boot :: (v0.5.0.M6) 14:53:51,849 |-INFO in ch.qos.logback.core.joran.action.AppenderAction - About to instantiate appender of type [ch.qos.logback.core.ConsoleAppender] 14:53:51,854 |-INFO in ch.qos.logback.core.joran.action.AppenderAction - Naming appender as [STDOUT] 14:53:51,854 |-INFO in ch.qos.logback.core.joran.action.NestedComplexPropertyIA - Assuming default type [ch.qos.logback.classic.encoder.PatternLayoutEncoder] for [encoder] property 14:53:51,855 |-INFO in ch.qos.logback.classic.joran.action.RootLoggerAction - Setting level of ROOT logger to INFO 14:53:51,856 |-INFO in ch.qos.logback.core.joran.action.AppenderRefAction - Attaching appender named [STDOUT] to Logger[ROOT] 14:53:51,856 |-INFO in ch.qos.logback.classic.joran.action.ConfigurationAction - End of configuration. 14:53:51,856 |-INFO in ch.qos.logback.classic.joran.JoranConfigurator@722b9406 - Registering current configuration as safe fallback point 14:53:51.945 INFO o.s.c.a.AnnotationConfigApplicationContext - Refreshing org.springframework.context.annotation.AnnotationConfigApplicationContext@6490832e: startup date [Thu Dec 19 14:53:51 GMT 2013]; root of context hierarchy 14:53:52.829 INFO o.s.b.f.s.DefaultListableBeanFactory - Overriding bean definition for bean 'transactionManager': replacing [Root bean: class [null]; scope=; abstract=false; lazyInit=false; autowireMode=3; dependencyCheck=0; autowireCandidate=true; primary=false; factoryBeanName=bootApp; factoryMethodName=transactionManager; initMethodName=null; destroyMethodName=(inferred); defined in class test.builder.BootApp] with [Root bean: class [null]; scope=; abstract=false; lazyInit=false; autowireMode=3; dependencyCheck=0; autowireCandidate=true; primary=false; factoryBeanName=org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration; factoryMethodName=transactionManager; initMethodName=null; destroyMethodName=(inferred); defined in class path resource [org/springframework/boot/autoconfigure/orm/jpa/HibernateJpaAutoConfiguration.class]] 14:53:52.830 INFO o.s.b.f.s.DefaultListableBeanFactory - Overriding bean definition for bean 'entityManagerFactory': replacing [Root bean: class [null]; scope=; abstract=false; lazyInit=false; autowireMode=3; dependencyCheck=0; autowireCandidate=true; primary=false; factoryBeanName=bootApp; factoryMethodName=entityManagerFactory; initMethodName=null; destroyMethodName=(inferred); defined in class test.builder.BootApp] with [Root bean: class [null]; scope=; abstract=false; lazyInit=false; autowireMode=3; dependencyCheck=0; autowireCandidate=true; primary=false; factoryBeanName=org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration; factoryMethodName=entityManagerFactory; initMethodName=null; destroyMethodName=(inferred); defined in class path resource [org/springframework/boot/autoconfigure/orm/jpa/HibernateJpaAutoConfiguration.class]] 14:53:52.830 INFO o.s.b.f.s.DefaultListableBeanFactory - Overriding bean definition for bean 'jpaVendorAdapter': replacing [Root bean: class [null]; scope=; abstract=false; lazyInit=false; autowireMode=3; dependencyCheck=0; autowireCandidate=true; primary=false; factoryBeanName=bootApp; factoryMethodName=jpaVendorAdapter; initMethodName=null; destroyMethodName=(inferred); defined in class test.builder.BootApp] with [Root bean: class [null]; scope=; abstract=false; lazyInit=false; autowireMode=3; dependencyCheck=0; autowireCandidate=true; primary=false; factoryBeanName=org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration; factoryMethodName=jpaVendorAdapter; initMethodName=null; destroyMethodName=(inferred); defined in class path resource [org/springframework/boot/autoconfigure/orm/jpa/HibernateJpaAutoConfiguration.class]] Exception in thread "main" 14:53:53.382 INFO o.s.b.a.AutoConfigurationReportLoggingInitializer$AutoConfigurationReportLogger - ========================= AUTO-CONFIGURATION REPORT ========================= Positive matches: ----------------- MessageSourceAutoConfiguration - @ConditionalOnMissingBean (types: org.springframework.context.MessageSource; SearchStrategy: all) found no beans (OnBeanCondition) AopAutoConfiguration - @ConditionalOnClass classes found: org.springframework.context.annotation.EnableAspectJAutoProxy,org.aspectj.lang.annotation.Aspect,org.aspectj.lang.reflect.Advice (OnClassCondition) - SpEL expression on org.springframework.boot.autoconfigure.aop.AopAutoConfiguration: #{true} (OnExpressionCondition) - @ConditionalOnClass classes found: org.springframework.context.annotation.EnableAspectJAutoProxy,org.aspectj.lang.annotation.Aspect,org.aspectj.lang.reflect.Advice (OnClassCondition) - SpEL expression on org.springframework.boot.autoconfigure.aop.AopAutoConfiguration: #{true} (OnExpressionCondition) AopAutoConfiguration.JdkDynamicAutoProxyConfiguration - SpEL expression on org.springframework.boot.autoconfigure.aop.AopAutoConfiguration$JdkDynamicAutoProxyConfiguration: #{!false} (OnExpressionCondition) - SpEL expression on org.springframework.boot.autoconfigure.aop.AopAutoConfiguration$JdkDynamicAutoProxyConfiguration: #{!false} (OnExpressionCondition) DataSourceAutoConfiguration - @ConditionalOnClass classes found: org.springframework.jdbc.datasource.embedded.EmbeddedDatabaseType (OnClassCondition) - @ConditionalOnClass classes found: org.springframework.jdbc.datasource.embedded.EmbeddedDatabaseType (OnClassCondition) DataSourceAutoConfiguration.JdbcTemplateConfiguration - existing auto database detected (DataSourceAutoConfiguration.DatabaseCondition) - existing auto database detected (DataSourceAutoConfiguration.DatabaseCondition) DataSourceAutoConfiguration.JdbcTemplateConfiguration#jdbcTemplate - @ConditionalOnMissingBean (types: org.springframework.jdbc.core.JdbcOperations; SearchStrategy: all) found no beans (OnBeanCondition) DataSourceAutoConfiguration.JdbcTemplateConfiguration#namedParameterJdbcTemplate - @ConditionalOnMissingBean (types: org.springframework.jdbc.core.namedparam.NamedParameterJdbcOperations; SearchStrategy: all) found no beans (OnBeanCondition) DataSourceTransactionManagerAutoConfiguration - @ConditionalOnClass classes found: org.springframework.jdbc.core.JdbcTemplate,org.springframework.transaction.PlatformTransactionManager (OnClassCondition) - @ConditionalOnClass classes found: org.springframework.jdbc.core.JdbcTemplate,org.springframework.transaction.PlatformTransactionManager (OnClassCondition) HibernateJpaAutoConfiguration - @ConditionalOnClass classes found: org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean,org.springframework.transaction.annotation.EnableTransactionManagement,javax.persistence.EntityManager,org.hibernate.ejb.HibernateEntityManager (OnClassCondition) - @ConditionalOnClass classes found: org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean,org.springframework.transaction.annotation.EnableTransactionManagement,javax.persistence.EntityManager,org.hibernate.ejb.HibernateEntityManager (OnClassCondition) - @ConditionalOnBean (types: javax.sql.DataSource; SearchStrategy: all) found the following [dataSource] (OnBeanCondition) ServerPropertiesAutoConfiguration#serverProperties - @ConditionalOnMissingBean (types: org.springframework.boot.context.embedded.properties.ServerProperties; SearchStrategy: all) found no beans (OnBeanCondition) Negative matches: ----------------- PropertyPlaceholderAutoConfiguration#propertySourcesPlaceholderConfigurer - @ConditionalOnMissingBean (types: org.springframework.context.support.PropertySourcesPlaceholderConfigurer; SearchStrategy: current) found the following [placeHolderConfigurer] (OnBeanCondition) RabbitAutoConfiguration - required @ConditionalOnClass classes not found: org.springframework.amqp.rabbit.core.RabbitTemplate,com.rabbitmq.client.Channel (OnClassCondition) AopAutoConfiguration.CglibAutoProxyConfiguration - SpEL expression on org.springframework.boot.autoconfigure.aop.AopAutoConfiguration$CglibAutoProxyConfiguration: #{false} (OnExpressionCondition) BatchAutoConfiguration - required @ConditionalOnClass classes not found: org.springframework.batch.core.launch.JobLauncher (OnClassCondition) JpaRepositoriesAutoConfiguration - @ConditionalOnClass classes found: org.springframework.data.jpa.repository.JpaRepository (OnClassCondition) - @ConditionalOnMissingBean (types: org.springframework.data.jpa.repository.support.JpaRepositoryFactoryBean; SearchStrategy: all) found the following [&builderRepository] (OnBeanCondition) JpaRepositoriesAutoConfiguration.JpaWebConfiguration - web application classes not found (OnWebApplicationCondition) MongoRepositoriesAutoConfiguration - required @ConditionalOnClass classes not found: com.mongodb.Mongo,org.springframework.data.mongodb.repository.MongoRepository (OnClassCondition) DataSourceAutoConfiguration.DbcpConfiguration - tomcat DataSource (DataSourceAutoConfiguration.BasicDatabaseCondition) DataSourceAutoConfiguration.EmbeddedConfiguration - existing non-embedded database detected (DataSourceAutoConfiguration.EmbeddedDatabaseCondition) DataSourceAutoConfiguration.TomcatConfiguration - found database driver com.microsoft.sqlserver.jdbc.SQLServerDriver (DataSourceAutoConfiguration.TomcatDatabaseCondition) - found database driver com.microsoft.sqlserver.jdbc.SQLServerDriver (DataSourceAutoConfiguration.TomcatDatabaseCondition) - @ConditionalOnMissingBean (types: javax.sql.DataSource; SearchStrategy: all) found the following [dataSource] (OnBeanCondition) DataSourceTransactionManagerAutoConfiguration#transactionManager - @ConditionalOnMissingBean (names: transactionManager; SearchStrategy: all) found the following [transactionManager] (OnBeanCondition) JmsTemplateAutoConfiguration - required @ConditionalOnClass classes not found: org.springframework.jms.core.JmsTemplate,javax.jms.ConnectionFactory (OnClassCondition) DeviceResolverAutoConfiguration - required @ConditionalOnClass classes not found: org.springframework.mobile.device.DeviceResolverHandlerInterceptor,org.springframework.mobile.device.DeviceHandlerMethodArgumentResolver (OnClassCondition) JpaBaseConfiguration.JpaWebConfiguration - web application classes not found (OnWebApplicationCondition) ReactorAutoConfiguration - required @ConditionalOnClass classes not found: reactor.spring.context.config.EnableReactor (OnClassCondition) ThymeleafAutoConfiguration - required @ConditionalOnClass classes not found: org.thymeleaf.spring3.SpringTemplateEngine (OnClassCondition) DispatcherServletAutoConfiguration - web application classes not found (OnWebApplicationCondition) EmbeddedServletContainerAutoConfiguration - web application classes not found (OnWebApplicationCondition) MultipartAutoConfiguration - required @ConditionalOnClass classes not found: javax.servlet.Servlet,org.springframework.web.multipart.support.StandardServletMultipartResolver (OnClassCondition) WebMvcAutoConfiguration - web application classes not found (OnWebApplicationCondition) WebSocketAutoConfiguration - required @ConditionalOnClass classes not found: org.springframework.web.socket.WebSocketHandler (OnClassCondition) org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'entityManagerFactory' defined in class path resource [org/springframework/boot/autoconfigure/orm/jpa/HibernateJpaAutoConfiguration.class]: Instantiation of bean failed; nested exception is org.springframework.beans.factory.BeanDefinitionStoreException: Factory method [public org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean org.springframework.boot.autoconfigure.orm.jpa.JpaBaseConfiguration.entityManagerFactory()] threw exception; nested exception is java.lang.IllegalArgumentException: Unable to find JPA packages to scan, please define a @ComponentScan annotation or disable JpaAutoConfiguration at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:584) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1089) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:984) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:504) at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:475) at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:300) at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:228) at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:296) at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:195) at org.springframework.context.support.AbstractApplicationContext.getBean(AbstractApplicationContext.java:973) at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:750) at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:482) at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:552) at org.springframework.boot.SpringApplication.run(SpringApplication.java:293) at org.springframework.boot.SpringApplication.run(SpringApplication.java:749) at org.springframework.boot.SpringApplication.run(SpringApplication.java:738) at test.builder.BootApp.main(BootApp.java:104) Caused by: org.springframework.beans.factory.BeanDefinitionStoreException: Factory method [public org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean org.springframework.boot.autoconfigure.orm.jpa.JpaBaseConfiguration.entityManagerFactory()] threw exception; nested exception is java.lang.IllegalArgumentException: Unable to find JPA packages to scan, please define a @ComponentScan annotation or disable JpaAutoConfiguration at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:188) at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:573) ... 16 more Caused by: java.lang.IllegalArgumentException: Unable to find JPA packages to scan, please define a @ComponentScan annotation or disable JpaAutoConfiguration at org.springframework.util.Assert.notEmpty(Assert.java:268) at org.springframework.boot.autoconfigure.orm.jpa.JpaBaseConfiguration.getPackagesToScan(JpaBaseConfiguration.java:109) at org.springframework.boot.autoconfigure.orm.jpa.JpaBaseConfiguration.entityManagerFactory(JpaBaseConfiguration.java:76) at org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration$$EnhancerByCGLIB$$7973d544.CGLIB$entityManagerFactory$4() at org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration$$EnhancerByCGLIB$$7973d544$$FastClassByCGLIB$$360fed5a.invoke( ) at org.springframework.cglib.proxy.MethodProxy.invokeSuper(MethodProxy.java:228) at org.springframework.context.annotation.ConfigurationClassEnhancer$BeanMethodInterceptor.intercept(ConfigurationClassEnhancer.java:334) at org.springframework.boot.autoconfigure.orm.jpa.HibernateJpaAutoConfiguration$$EnhancerByCGLIB$$7973d544.entityManagerFactory( ) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) at java.lang.reflect.Method.invoke(Method.java:597) at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:166) ... 17 more
Pom提取物 -
org.springframework.boot spring-boot-starter-parent 0.5.0.M6 org.springframework.boot spring-boot-starter-data-jpa org.apache.tomcat tomcat-jdbc com.microsoft.sqlserver sqljdbc4 4.0 ch.qos.logback logback-core 1.0.13 ch.qos.logback logback-classic org.slf4j slf4j-api
任何建议表示赞赏
你的@Repository接口在哪里?
Spring Data可以为您创建各种风格的@Repository接口的实现.只要这些@Repositories包含在@EnableAutoConfiguration类的同一个包(或子包)中,Spring Boot就会为您处理所有这些.
http://projects.spring.io/spring-boot/docs/docs/howto.html
这是因为Spring Boot想要为你创建存储库,而你却没有告诉它它们在哪里.你需@ComponentScan
要这样做(我认为错误信息至少在最近的版本中是这样说的).您的应用程序正在做很多不需要的东西.这应该工作:
@Configuration @EnableAutoConfiguration @ComponentScan("test.builder") public class BootApp implements CommandLineRunner { private static Logger logger = LoggerFactory.getLogger(BootApp.class); @Autowired private BuilderRepository repository; @Override public void run(String... args) { Builder builder = repository.findOne(10); logger.info("Retrieved ", builder.toString()); } public static void main(String[] args) { SpringApplication.run(BootApp.class, args); } }