包结构会影响托管类

时间:2016-02-11 08:32:59

标签: java spring-boot packages

我有几个Spring启动项目。出于这个问题的目的,让我说我有这些类的以下项目:

MyProject的-公地: cz.myproject.commons.model.MyEntity;

MyProject的工人: cz.myproject.worker.repository.EntityRepository;

MyProject-workerMyProject-commons作为maven依赖。

EntityRepositoryMyEntity的一个Spring JPA存储库:

public interface ImageMetadataRepository extends CrudRepository<MyEntity, Long> {
}

问题是我总是通过此设置获得以下异常:

org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'EntityRepository': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Not an managed type: class cz.myproject.commons.model.MyEntity

如果我将存储库移动到以下包(cz.myproject.repository.EntityRepository),一切都会开始工作!我很困惑为什么包结构会影响这样的行为。

有人可以解释发生了什么,我怎样才能使用我描述的包结构?感谢您的任何提示!

我的Spring启动application.java:

@SpringBootApplication
@EnableJpaRepositories(basePackages = "cz.myproject.worker.repository")
@EntityScan(basePackages = "cz.myproject.commons.model")
public class Application extends SpringBootServletInitializer {

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

2 个答案:

答案 0 :(得分:1)

Spring Boot会扫描@Entity个类,如果它们放在您指定@SpringBootApplication注释的相同包或子包中。

您必须使用@EntityScan注释,因为Entities位于其他包中。

@EntityScan(basePackages = "cz.myproject.commons.model")

@EntityScan(basePackageClasses=MyEntity.class)

我们可以使用basePackages,而不是指定basePackageClasses属性,以便扫描存在package的{​​{1}}。

从春季训练documentation -

  

MyEntity.java

     

配置   LocalContainerEntityManagerFactoryBean用于扫描实体类   类路径。此注释提供了手动替代方法   设置   LocalContainerEntityManagerFactoryBean.setPackagesToScan(字符串...)   如果要配置实体扫描,则特别有用   一种类型安全的方法,或者如果你的LocalContainerEntityManagerFactoryBean是   自动配置。必须是LocalContainerEntityManagerFactoryBean   在Spring ApplicationContext中配置以便使用   实体扫描。此外,任何现有的packagesToScan设置都将   被替换。

     

basePackageClasses(),basePackages()或其别名值()之一可以   指定用于定义要扫描的特定包。如果具体包装   未定义扫描将从类的包中发生   这个注释。

答案 1 :(得分:0)

在资源文件夹中的META-INF文件夹中,确保您有persistance.xml,您必须具有MyEntity全名,如下所示 cz.myproject.commons.model.MyEntity,如果您在包中具有公共元数据,请确保您在应用程序上下文中具有以下内容

<bean class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean" id="myEMF">
        <property name="persistenceXmlLocation" value="classpath:META-INF/persistence.xml" />
        <property name="persistenceUnitName" value="YOUR_PU" />
        <property name="jpaVendorAdapter" ref="hibernateJpaAdapter" />
        <property name="jpaProperties">
             <props>
                <prop key="hibernate.hbm2ddl.auto">none</prop>
            </props>
        </property>

    </bean>

如果jar中有persistance.xml,那么你必须在路径

之前有classpath:

如果您使用类上下文,请确保在实体bean创建中具有以下内容

@Bean
   public LocalContainerEntityManagerFactoryBean entityManagerFactory() {
      LocalContainerEntityManagerFactoryBean em = new LocalContainerEntityManagerFactoryBean();
      em.setDataSource(dataSource());
      em.setPackagesToScan(new String[] { "cz.myproject.commons.model" });

      JpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
      em.setJpaVendorAdapter(vendorAdapter);
      em.setJpaProperties(additionalProperties());

      return em;
   }