2015-02-24 6 views
5

Ich bin neu in Spring Framework. Ich habe gerade begonnen zu lernen, verschiedene Guides (http://spring.io/guides) zu folgen und ich versuche, das vollständige Tutorial über Web-Services (http://spring.io/guides/tutorials/bookmarks/) zu vervollständigen.Spring Data Repository - Keine qualifizierende Bean Injection

Ich bin ganz auf der PPV-Datenquelle Definition stecken, weil ich die folgenden Fehler

Exception in thread "main" org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'init' defined in main.Application: Unsatisfied dependency expressed through constructor argument with index 0 of type [bookmarks.AccountRepository]: : No qualifying bean of type [bookmarks.AccountRepository] found for dependency: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {}; nested exception is org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type [bookmarks.AccountRepository] found for dependency: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {} 
    at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:749) 
    at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:464) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1111) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1006) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:504) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:476) 
    at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:303) 
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) 
    at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:299) 
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:194) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:762) 
    at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:757) 
    at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:480) 
    at org.springframework.boot.context.embedded.EmbeddedWebApplicationContext.refresh(EmbeddedWebApplicationContext.java:118) 
    at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:691) 
    at org.springframework.boot.SpringApplication.run(SpringApplication.java:321) 
    at org.springframework.boot.SpringApplication.run(SpringApplication.java:961) 
    at org.springframework.boot.SpringApplication.run(SpringApplication.java:950) 
    at main.Application.main(Application.java:41) 
Caused by: org.springframework.beans.factory.NoSuchBeanDefinitionException: No qualifying bean of type [bookmarks.AccountRepository] found for dependency: expected at least 1 bean which qualifies as autowire candidate for this dependency. Dependency annotations: {} 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.raiseNoSuchBeanDefinitionException(DefaultListableBeanFactory.java:1308) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1054) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:949) 
    at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:813) 
    at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:741) 
    ... 18 more 

Meine Hauptanwendungsklasse erhalte, ist die folgende

@Configuration 
@ComponentScan 
@EnableAutoConfiguration 
public class Application { 

    @Bean 
    public CommandLineRunner init(AccountRepository accountRepository, 
      BookmarkRepository bookmarkRepository) { 
     System.out.println("Bean!"); 
     return (evt) -> Arrays.asList(
       "jhoeller,dsyer,pwebb,ogierke,rwinch,mfisher,mpollack,jlong".split(",")) 
       .forEach(
         a -> { 
          Account account = accountRepository.save(new Account(a, 
            "password")); 
          bookmarkRepository.save(new Bookmark(account, 
            "http://bookmark.com/1/" + a, "A description")); 
          bookmarkRepository.save(new Bookmark(account, 
            "http://bookmark.com/2/" + a, "A description")); 
         }); 
    } 

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

Und meine pom.xml ist

<?xml version="1.0" encoding="UTF-8"?> 
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> 
    <modelVersion>4.0.0</modelVersion> 

    <groupId>org.test</groupId> 
    <artifactId>demo</artifactId> 
    <version>0.0.1</version> 
    <packaging>jar</packaging> 

    <name>demo</name> 
    <description>Demo project for Spring Boot</description> 

    <parent> 
     <groupId>org.springframework.boot</groupId> 
     <artifactId>spring-boot-starter-parent</artifactId> 
     <version>1.2.1.RELEASE</version> 
     <relativePath /> <!-- lookup parent from repository --> 
    </parent> 

    <properties> 
     <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> 
     <start-class>demo.DemoApplication</start-class> 
     <java.version>1.8</java.version> 
    </properties> 

    <dependencies> 
     <dependency> 
      <groupId>org.springframework.boot</groupId> 
      <artifactId>spring-boot-starter-web</artifactId> 
     </dependency> 
     <dependency> 
      <groupId>org.springframework.boot</groupId> 
      <artifactId>spring-boot-starter-test</artifactId> 
      <scope>test</scope> 
     </dependency> 
     <dependency> 
      <groupId>org.springframework.boot</groupId> 
      <artifactId>spring-boot-starter-data-jpa</artifactId> 
     </dependency> 
     <dependency> 
      <groupId>org.springframework.data</groupId> 
      <artifactId>spring-data-jpa</artifactId> 
     </dependency> 
     <dependency> 
      <groupId>com.h2database</groupId> 
      <artifactId>h2</artifactId> 
     </dependency> 
     <dependency> 
      <groupId>javax.inject</groupId> 
      <artifactId>javax.inject</artifactId> 
      <version>1</version> 
     </dependency> 
    </dependencies> 

    <build> 
     <plugins> 
      <plugin> 
       <groupId>org.springframework.boot</groupId> 
       <artifactId>spring-boot-maven-plugin</artifactId> 
      </plugin> 
     </plugins> 
    </build> 

</project> 

Ich verstehe, dass die Dependency Injection-Framework findet keine Umsetzung der AccountRepository-Schnittstelle, die

public interface AccountRepository extends JpaRepository<Account, Long> { 
    Optional<Account> findByUsername(String username); 
} 

Aber der Rahmen sollte bieten wie

sieht „eine korrekte Umsetzung“ für die JpaRepository. Dies ist der Teil, den ich nicht verstehe.

Jede Hilfe würde geschätzt, insbesondere mit einem Zeiger, in diesem Rahmen zu studieren.

Dank

UPDATE @EnableJpaRepositories ("Lesezeichen") an die Anwendungsklasse, gelöst Hinzufügen der Bohne Auflösung Problem. Aber jetzt bin erhalten Verursacht durch: java.lang.IllegalArgumentException: Nicht ein verwalteten Typ: Klasse bookmarks.Account

Ihr Konto Entitätsklasse ist

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

import com.fasterxml.jackson.annotation.JsonIgnore; 

@Entity 
public class Account { 

    @JsonIgnore 
    public String password; 
    public String username; 
    @OneToMany(mappedBy="Account") 
    private Set<Bookmark> bookmarks = new HashSet<>(); 
    @Id @GeneratedValue 
    private Long id; 

    public Account(String name, String password) { 
     this.username = name; 
     this.password = password; 
    } 

    Account() { } // jpa only 

    // getters and setters 
} 
+0

, welche Pakete sind Ihre Repositories in? – farrellmr

+0

Meine Projektstruktur ist die folgende: src/main/java Lesezeichen Account.java AccountRepository.java Haupt Application.java so die Repositories in den Paket Lesezeichen sind. – besil

+0

ID laden Sie die Quelle und arbeiten Sie von dort - https://github.com/spring-guides/tut-bookmarks/blob/master/rest/src/main/java/bookmarks/Application.java - nicht viel Hilfe - aber Sie arbeiten das Tutorial – farrellmr

Antwort

10

Für JpaRepository von Rahmen ausgewählt werden, müssen Sie Aktivieren Sie es in Ihrer Konfiguration - hinzufügen

@EnableJpaRepositories("your.package.with.jpa.repositories") 

in Ihrer @Configuration Datei.


upd

hier Beispielkonfiguration für JPA-Repositories zu arbeiten:

@Bean 
public DataSource dataSource(){ 
    // configure your datasource 
} 

@Bean 
public LocalContainerEntityManagerFactoryBean entityManagerFactory(DataSource dataSource) { 
    LocalContainerEntityManagerFactoryBean emfb = new LocalContainerEntityManagerFactoryBean(); 
    emfb.setDataSource(dataSource); 
    emfb.setPackagesToScan("your.package.with.model"); 
    emfb.setJpaVendorAdapter(jpaVendorAdapter()); 
    emfb.setJpaPropertyMap(jpaPropertiesMap()); 
    return emfb; 
} 

@Bean 
public JpaVendorAdapter jpaVendorAdapter() { 
    return new HibernateJpaVendorAdapter(); 
} 

@Bean 
public PlatformTransactionManager transactionManager(EntityManagerFactory emf) { 
    JpaTransactionManager transactionManager = new JpaTransactionManager(); 
    transactionManager.setEntityManagerFactory(emf); 
    return transactionManager; 
} 

public Map<String, ?> jpaPropertiesMap() { 
    Properties properties = new Properties(); 
    properties.setProperty("hibernate.dialect", "org.hibernate.dialect.H2Dialect"); // assumption based on your pom-file 
    properties.setProperty("hibernate.hbm2ddl.auto", "..."); // you need to google for appropriate option 
    return properties; 
} 
+0

Vielen Dank für die Antwort. Ich habe @EnableJpaRepositories ("Lesezeichen") Annotation auf der Hauptklasse "Application", aber jetzt bin ich den folgenden Fehler erhalten java.lang.IllegalArgumentException: Kein verwalteter Typ: class bookmarks.Account. Die Kontoklasse ist eine @Entity annotierte Klasse – besil

+0

@besil gut, da Sie 'JpaRepository' verwenden, muss Ihr' Account' zu Sei jpa entity, es sollte mit '@ Entity' versehen sein und eine id-Eigenschaft haben - mit '@ Id' versehen. – Vladimir

+0

Ja, das ist es .. Die Bean-Entity-Auflösung scheint jetzt zu funktionieren, aber ich tue es nicht Verstehen Sie, warum die Klasse Account den Fehler – besil

2

Der letzte (in Betrieb) Konfiguration für die Probleme lösen, ist die folgende (nur die Dokumentation folgende http://spring.io/guides/tutorials/bookmarks/).

Die Lösung wurde Zugabe

<dependency> 
    <groupId>com.h2database</groupId> 
    <artifactId>h2</artifactId> 
</dependency> 

im pom.xml, und die

@OneToMany(mappedBy = "account") 
private Set<Bookmark> bookmarks = new HashSet<>(); 

in der Klasse Konto zu ändern (der Fehler war: mappedBy = "Konto", Großbuchstaben ...).

Voll Code unten:

pom.xml

<?xml version="1.0" encoding="UTF-8"?> 
<project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" 
    xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> 
    <modelVersion>4.0.0</modelVersion> 

    <groupId>org.test</groupId> 
    <artifactId>demo</artifactId> 
    <version>0.0.1-SNAPSHOT</version> 
    <packaging>jar</packaging> 

    <name>MyRestService</name> 
    <description>Demo project for Spring Boot</description> 

    <parent> 
     <groupId>org.springframework.boot</groupId> 
     <artifactId>spring-boot-starter-parent</artifactId> 
     <version>1.2.1.RELEASE</version> 
     <relativePath/> <!-- lookup parent from repository --> 
    </parent> 

    <properties> 
     <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> 
     <start-class>demo.MyRestServiceApplication</start-class> 
     <java.version>1.8</java.version> 
    </properties> 

    <dependencies> 
     <dependency> 
      <groupId>org.springframework.boot</groupId> 
      <artifactId>spring-boot-starter-web</artifactId> 
     </dependency> 
     <dependency> 
      <groupId>org.springframework.boot</groupId> 
      <artifactId>spring-boot-starter-data-jpa</artifactId> 
     </dependency> 
     <dependency> 
      <groupId>org.springframework.boot</groupId> 
      <artifactId>spring-boot-starter-test</artifactId> 
      <scope>test</scope> 
     </dependency> 
     <dependency> 
      <groupId>com.h2database</groupId> 
      <artifactId>h2</artifactId> 
     </dependency> 
    </dependencies> 

    <build> 
     <plugins> 
      <plugin> 
       <groupId>org.springframework.boot</groupId> 
       <artifactId>spring-boot-maven-plugin</artifactId> 
      </plugin> 
     </plugins> 
    </build> 

</project> 

Konto Klasse

package bookmarks; 

import java.util.HashSet; 
import java.util.Set; 

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

import com.fasterxml.jackson.annotation.JsonIgnore; 

@Entity 
public class Account { 

    @OneToMany(mappedBy = "account") 
    private Set<Bookmark> bookmarks = new HashSet<>(); 

    @Id 
    @GeneratedValue 
    private Long id; 

    public Set<Bookmark> getBookmarks() { 
     return bookmarks; 
    } 

    public Long getId() { 
     return id; 
    } 

    public String getPassword() { 
     return password; 
    } 

    public String getUsername() { 
     return username; 
    } 

    @JsonIgnore 
    public String password; 
    public String username; 

    public Account(String name, String password) { 
     this.username = name; 
     this.password = password; 
    } 

    Account() { // jpa only 
    } 
} 

Anwendungsklasse

@Configuration 
@ComponentScan 
@EnableAutoConfiguration 
public class Application { 
    @Bean 
    CommandLineRunner init(AccountRepository accountRepository, 
      BookmarkRepository bookmarkRepository) { 
     return (evt) -> Arrays.asList(
       "jhoeller,dsyer,pwebb,ogierke,rwinch,mfisher,mpollack,jlong".split(",")) 
       .forEach(
         a -> { 
          Account account = accountRepository.save(new Account(a, 
            "password")); 
          bookmarkRepository.save(new Bookmark(account, 
            "http://bookmark.com/1/" + a, "A description")); 
          bookmarkRepository.save(new Bookmark(account, 
            "http://bookmark.com/2/" + a, "A description")); 
         }); 
    } 

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