Avvio a molla: non un tipo gestito


137

Uso Spring boot + JPA e ho un problema durante l'avvio del servizio.

Caused by: java.lang.IllegalArgumentException: Not an managed type: class com.nervytech.dialer.domain.PhoneSettings
    at org.hibernate.jpa.internal.metamodel.MetamodelImpl.managedType(MetamodelImpl.java:219)
    at org.springframework.data.jpa.repository.support.JpaMetamodelEntityInformation.<init>(JpaMetamodelEntityInformation.java:68)
    at org.springframework.data.jpa.repository.support.JpaEntityInformationSupport.getMetadata(JpaEntityInformationSupport.java:65)
    at org.springframework.data.jpa.repository.support.JpaRepositoryFactory.getEntityInformation(JpaRepositoryFactory.java:145)
    at org.springframework.data.jpa.repository.support.JpaRepositoryFactory.getTargetRepository(JpaRepositoryFactory.java:89)
    at org.springframework.data.jpa.repository.support.JpaRepositoryFactory.getTargetRepository(JpaRepositoryFactory.java:69)
    at org.springframework.data.repository.core.support.RepositoryFactorySupport.getRepository(RepositoryFactorySupport.java:177)
    at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.initAndReturn(RepositoryFactoryBeanSupport.java:239)
    at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.afterPropertiesSet(RepositoryFactoryBeanSupport.java:225)
    at org.springframework.data.jpa.repository.support.JpaRepositoryFactoryBean.afterPropertiesSet(JpaRepositoryFactoryBean.java:92)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1625)
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1562)

Ecco il file Application.java,

@Configuration
@ComponentScan
@EnableAutoConfiguration(exclude = { DataSourceAutoConfiguration.class })
@SpringBootApplication
public class DialerApplication {

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

Uso UCp per il pool di connessioni e la configurazione di DataSource è di seguito,

@Configuration
@ComponentScan
@EnableTransactionManagement
@EnableAutoConfiguration
@EnableJpaRepositories(entityManagerFactoryRef = "dialerEntityManagerFactory", transactionManagerRef = "dialerTransactionManager", basePackages = { "com.nervy.dialer.spring.jpa.repository" })
public class ApplicationDataSource {

    /** The Constant LOGGER. */
    private static final Logger LOGGER = LoggerFactory
            .getLogger(ApplicationDataSource.class);

    /** The Constant TEST_SQL. */
    private static final String TEST_SQL = "select 1 from dual";

    /** The pooled data source. */
    private PoolDataSource pooledDataSource;

Implementazione UserDetailsService,

@Service("userDetailsService")
@SessionAttributes("user")
public class UserDetailsServiceImpl implements UserDetailsService {

    @Autowired
    private UserService userService;

Implementazione del livello di servizio,

@Service
public class PhoneSettingsServiceImpl implements PhoneSettingsService {

}

La classe del repository,

@Repository
public interface PhoneSettingsRepository extends JpaRepository<PhoneSettings, Long> {

}

Classe di entità,

@Entity
@Table(name = "phone_settings", catalog = "dialer")
public class PhoneSettings implements java.io.Serializable {

Classe WebSecurityConfig,

@Configuration
@EnableWebMvcSecurity
@ComponentScan
public class WebSecurityConfig extends WebSecurityConfigurerAdapter {

    @Autowired
    private UserDetailsServiceImpl userDetailsService;

    /**
     * Instantiates a new web security config.
     */
    public WebSecurityConfig() {

        super();
    }

    /**
     * {@inheritDoc}
     * @see org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter#configure(org.springframework.security.config.annotation.web.builders.HttpSecurity)
     */
    @Override
    protected void configure(HttpSecurity http) throws Exception {

        http.authorizeRequests()
            .antMatchers("/login", "/logoffUser", "/sessionExpired", "/error", "/unauth", "/redirect", "*support*").permitAll()
            .anyRequest().authenticated().and().rememberMe().and().httpBasic()
            .and()
            .csrf()
            .disable().logout().deleteCookies("JSESSIONID").logoutSuccessUrl("/logoff").invalidateHttpSession(true);
    }


    @Autowired
    public void configAuthentication(AuthenticationManagerBuilder auth) throws Exception {

      auth.userDetailsService(userDetailsService).passwordEncoder(new BCryptPasswordEncoder());
    }

}

I pacchetti sono i seguenti,

  1. Application la lezione è in - com.nervy.dialer
  2. Datasource la lezione è in - com.nervy.dialer.common
  3. Le classi di entità sono in - com.nervy.dialer.domain
  4. Le classi di servizio sono in - com.nervy.dialer.domain.service.impl
  5. I controller sono in - com.nervy.dialer.spring.controller
  6. Le classi del repository sono in - com.nervy.dialer.spring.jpa.repository
  7. WebSecurityConfig è in - com.nervy.dialer.spring.security

Grazie


1
Credo che dovrai ancora dire a Hibernate di scansionare il pacchetto per il tuo oggetto entità.
Chrylis

Risposte:


51

Penso che la sostituzione @ComponentScancon @ComponentScan("com.nervy.dialer.domain")funzionerà.

Modificare :

Ho aggiunto un'applicazione di esempio per dimostrare come impostare una connessione di origine dati in pool con BoneCP.

L'applicazione ha la stessa struttura con la tua. Spero che questo ti aiuti a risolvere i tuoi problemi di configurazione


Se aggiungo @ComponentScan ("com.nervy.dialer.domain"), sto ottenendo un'origine dati non un'eccezione poiché si trova in un pacchetto diverso. Aggiunto quel pacchetto come @ComponentScan ({"com.nervy.dialer.domain", "com.nervy.dialer.common"}). Ora ottiene lo stesso vecchio errore.
user1578872

1
Ho aggiunto un'applicazione di esempio per dimostrare come impostare una connessione di origine dati in pool con BoneCP. github.com/azizunsal/SpringBootBoneCPPooledDataSource L'applicazione ha la stessa struttura con la tua. Spero che questo ti aiuti a risolvere i tuoi problemi di configurazione.
Azizunsal,

Hai fatto la magia. Funziona bene Grazie per l'aiuto. Ho avuto la seguente annotazione nell'origine dati. @EnableJpaRepositories (entityManagerFactoryRef = "dialerEntityManagerFactory", transactionManagerRef = "dialerTransactionManager", basePackages = {"com.nervytech.dialer.repository"}). Dopo aver rimosso questo e appena aggiunto @EnableJpsRespository in DialerApplication, ha iniziato a funzionare correttamente.
user1578872,

Ho lo stesso problema. L'avvio a molla non riconosce la mia entità (@DynamicUpdate dalla versione 4+ di ibernazione). Ho provato ad aggiungere il mio pacchetto modello in ComponentScan o EntityScan e ho lo stesso errore. Le mie annotazioni nella classe Application sono: SpringBootApplication ComponentScan (basePackages = {"com.example.controllers", "com.example.services", "com.example.models"}) EnableAutoConfiguration @Configuration @EnableJpaRepositories (basePackages = {"com. example.dao "," com.example.models "})
Balflear,

Lo stesso scenario che abbiamo utilizzato Hibernated come provider JPA. Come dopo aver provato tutte queste soluzioni, il problema esiste ancora. Aggiunta questa configurazione nel mio file di configurazione dell'applicazione risolto il problema per me. hibernate.annotation.packages.to.scan = $ {myEntityPackage}
Robin,

112

Configurare la posizione delle entità utilizzando @EntityScan nella classe del punto di ingresso di Spring Boot.

Aggiornamento di settembre 2016 : per Spring Boot 1.4+:
utilizzare org.springframework.boot.autoconfigure.domain.EntityScan
anziché org.springframework.boot.orm.jpa.EntityScan, poiché ... boot.orm.jpa.EntityScan è obsoleto a partire da Spring Boot 1.4


2
Anche questa opzione non aiuta. Immagino, mi manca qualcos'altro nella mia configurazione.
user1578872

3
Non aiuta anche nel mio caso.
Balflear,

1
Ha funzionato per me ma è un'annotazione deprecata.
Juan Carlos Puerto,

Grazie Juan, ho aggiornato la risposta con la versione corrente di Entity Scan.
Manish Maheshwari,

78

Prova ad aggiungere tutto quanto segue, Nella mia applicazione funziona bene con Tomcat

 @EnableJpaRepositories("my.package.base.*")
 @ComponentScan(basePackages = { "my.package.base.*" })
 @EntityScan("my.package.base.*")   

Sto usando l'avvio a molla e quando uso Tomcat incorporato funzionava bene senza, @EntityScan("my.package.base.*")ma quando ho provato a distribuire l'app su un Tomcat esterno ho ricevuto un not a managed typeerrore per la mia entità.


Tu sei il mio eroe.
Artur Łysik,

27

Nel mio caso il problema era dovuto alla mia dimenticanza di aver annotato le mie classi Entity con @javax.persistence.Entityannotazione. Doh!

//The class reported as "not a amanaged type"
@javax.persistence.Entity
public class MyEntityClass extends my.base.EntityClass {
    ....
}

Nel mio caso avevo anche bisogno del nome della tabella nell'annotazione @Entity. Ho creato un progetto di esempio qui: github.com/mate0021/two_datasources.git
mate00

22

Se la configurazione di persistenza è stata incollata e copiata da un altro progetto, è necessario impostare manualmente il pacchetto in EntityManagerFactory :

@Bean
public EntityManagerFactory entityManagerFactory() throws PropertyVetoException {
    HibernateJpaVendorAdapter vendorAdapter = new HibernateJpaVendorAdapter();
    vendorAdapter.setGenerateDdl(true);
    LocalContainerEntityManagerFactoryBean factory;
    factory = new LocalContainerEntityManagerFactoryBean();
    factory.setPackagesToScan("!!!!!!misspelled.package.path.to.entities!!!!!");
    //...
}

18

È possibile utilizzare l' annotazione @EntityScan e fornire il pacchetto entità per la scansione di tutte le entità jpa. È possibile utilizzare questa annotazione sulla classe dell'applicazione di base in cui è stata utilizzata l'annotazione @SpringBootApplication.

ad es. @EntityScan ("com.test.springboot.demo.entity")



12

Ho avuto questo errore perché ho scritto stupidamente

interfaccia pubblica FooBarRepository estende CrudRepository <FooBar Repository , Long> {...

Una breve spiegazione: in genere si crea una classe FooBarRepository per gestire gli oggetti FooBar (spesso rappresentano i dati in una tabella chiamata qualcosa come foo_bar.) Quando si estende CrudRepository per creare la classe di repository specializzata, è necessario specificare il tipo che viene gestito - in questo caso, FooBar. Ciò che ho erroneamente digitato, tuttavia, era FooBarRepository anziché FooBar. FooBarRepository non è il tipo (la classe) che sto cercando di gestire con FooBarRepository. Pertanto, il compilatore genera questo errore.

Ho evidenziato l'errore di digitare in grassetto . Elimina la parola evidenziata Repository nel mio esempio e il codice viene compilato.


6
15 minuti della mia vita che non riuscirò a recuperare
Oscar Moncayo,

@TayabHussain, ho aggiornato il post con alcune spiegazioni. Spero che ti aiuti.
Marvo

7

Metti questo nel tuo Application.javafile

@ComponentScan(basePackages={"com.nervy.dialer"})
@EntityScan(basePackages="domain")

Questo è un duplicato per la risposta sopra.
Keshu R.

6

Hai perso @Entity nella definizione della classe o hai un percorso di scansione del componente esplicito e questo percorso non contiene la tua classe


3

Sto usando Spring Boot 2.0 e ho risolto questo problema sostituendo @ComponentScan con @EntityScan


1

Ho avuto lo stesso problema, ma solo durante l'esecuzione dei casi di test di avvio a molla che richiedevano JPA. Il risultato finale è stato che la nostra configurazione di test jpa stava inizializzando un EntityManagerFactory e impostando i pacchetti per la scansione. Ciò evidentemente sovrascriverà i parametri EntityScan se lo si imposta manualmente.

    final LocalContainerEntityManagerFactoryBean factory = new LocalContainerEntityManagerFactoryBean();
    factory.setJpaVendorAdapter( vendorAdapter );
    factory.setPackagesToScan( Project.class.getPackage().getName());
    factory.setDataSource( dataSource );

Importante notare: se si è ancora bloccato si dovrebbe impostare un punto di interruzione nel org.springframework.orm.jpa.persistenceunit.DefaultPersistenceUnitManagersul setPackagesToScan()metodo e dare un'occhiata a dove questo viene chiamato e quali pacchetti vengono passati ad esso.


1

Ho avuto qualche problema durante la migrazione da Spring boot 1.3.xa 1.5, l'ho fatto funzionare dopo aver aggiornato il pacchetto di entità nel bean EntityManagerFactory

  @Bean(name="entityManagerFactoryDef")
  @Primary
  public LocalContainerEntityManagerFactoryBean defaultEntityManager() {
      Map map = new HashMap();
      map.put("hibernate.default_schema", env.getProperty("spring.datasource.username"));
      map.put("hibernate.hbm2ddl.auto", env.getProperty("spring.jpa.hibernate.ddl-auto"));
      LocalContainerEntityManagerFactoryBean em = createEntityManagerFactoryBuilder(jpaVendorProperties())
              .dataSource(primaryDataSource()).persistenceUnit("default").properties(map).build();
      em.setPackagesToScan("com.simple.entity");
      em.afterPropertiesSet();
      return em;
  }

Questo bean si riferiva alla classe Application come di seguito

@SpringBootApplication
@EnableJpaRepositories(entityManagerFactoryRef = "entityManagerFactoryDef")
public class SimpleApp {

}

0

Ho lo stesso probblem, nella versione Spring Boot v1.3.x quello che ho fatto è aggiornare Spring Boot alla versione 1.5.7.RELEASE. Quindi il probblem sparì.


Ero su una 1.3.x poi sono passato alla 1.5.6 e ho avuto il problema
apkisbossin

0

Ho avuto questo problema perché non ho mappato tutte le entità nel file orm.xml


0

Di seguito ha funzionato per me ..

import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get;
import static org.springframework.test.web.servlet.result.MockMvcResultHandlers.print;
import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status;

import org.apache.catalina.security.SecurityConfig;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.domain.EntityScan;
import org.springframework.boot.test.context.SpringBootTest;
import org.springframework.context.annotation.ComponentScan;
import org.springframework.data.jpa.repository.config.EnableJpaRepositories;
import org.springframework.test.context.junit4.SpringRunner;
import org.springframework.test.context.web.WebAppConfiguration;
import org.springframework.test.web.servlet.MockMvc;
import org.springframework.test.web.servlet.setup.MockMvcBuilders;
import org.springframework.web.context.WebApplicationContext;

import com.something.configuration.SomethingConfig;

@RunWith(SpringRunner.class)
@SpringBootTest(classes = { SomethingConfig.class, SecurityConfig.class }) //All your configuration classes
@EnableAutoConfiguration
@WebAppConfiguration // for MVC configuration
@EnableJpaRepositories("com.something.persistence.dataaccess")  //JPA repositories
@EntityScan("com.something.domain.entity.*")  //JPA entities
@ComponentScan("com.something.persistence.fixture") //any component classes you have
public class SomethingApplicationTest {

@Autowired
private WebApplicationContext ctx;
private MockMvc mockMvc;

@Before
public void setUp() {
    this.mockMvc = MockMvcBuilders.webAppContextSetup(ctx).build();
}

@Test
public void loginTest() throws Exception {
    this.mockMvc.perform(get("/something/login")).andDo(print()).andExpect(status().isOk());
}

}


0

Ho spostato la mia classe di applicazione nel pacchetto padre come:

Classe principale: com.job.application

Entità: com.job.application.entity

In questo modo non è necessario aggiungere @EntityScan

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.