ここに投稿されたチュートリアルに従って、Spring Data JPA で動作する基本アプリケーションを取得しました。今、私がどのように理解したか、構成を使用して
<jpa:repositories base-package="my.package.to.scan" />
そのパッケージは、Spring Data JPA によってスキャンされ、インターフェースが拡張され、JpaRepository
その concreate Bean が作成されるため、単純な Spring を使用してサービスクラスのどこでも使用できます@Autowired
。しかし、className を持つ Bean が見つからないことを示して失敗します (これは、Bean が作成時に取得するデフォルトの名前であり、単純に大文字化されていない ClassName を使用します)。
ただし、次のように applicationContext で Bean manualy を構成すると:
<bean id="ClassName" class="my.package.to.scan.ClassName"/>
春は豆を見つけることができます。もちろん、インターフェイスから Bean を作成したいのでエラーが発生しますが、明らかに機能しません。しかし、要点は、Spring Data JPA の「自動 Bean 作成」が何らかの形で失敗しているように見えるということです。
関連するコードを添付しましたので、参照してください。ところで、私はポートレットを開発していることに言及する必要があるので、なぜ私が spring-config を持っていないのか不思議に思う必要はありません。現在、ポートレット構成用に applicationConfig のみと MyPortlet-Portlet.xml を使用しています (ただし、この問題には関係ありません)。間違った注釈/クラスを使用していないことを確認するためだけに、インポートステートメントを追加しました。
applicationContext.xml
<beans *** ALL MY XMLN's and XSI's *** />
<context:annotation-config />
<jpa:repositories base-package="model.repositories" />
// JPA specific configuration here: dataSource, persistenceUnitManager exceptionTranslator, entityManagerFactory, SessionFactory, transactionManager - should not be relevant for this problem, tell me if i'm wrong
<bean class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor" />
ICustomerService - CustomerService の単なるインターフェース
import model.entities.Customer;
public interface ICustomerService {
// example method
public Customer getCustomer(Long customerId);
}
CustomerService - ORM データを取得/設定するためにアプリケーション ロジックで使用されるクラス
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.stereotype.Repository;
import org.springframework.transaction.annotation.Transactional;
import model.entities.Customer;
import model.repositories.CustomerRepository;
import model.service.interfaces.ICustomerService;
@Repository
@Transactional(readOnly = true)
public class CustomerService implements ICustomerService{
@Autowired
private CustomerRepository repository;
// example method
@Override
public Customer getCustomer(Long customerId){
return repository.findById(customerId);
}
CustomerRepository - Spring Data JPA のリポジトリ
import javax.annotation.Resource;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.transaction.annotation.Transactional;
import model.entities.Customer;
@Resource
@Transactional(readOnly = true)
public interface CustomerRepository extends JpaRepository<Customer, Long>{
public Customer findById(Long id);
}
顧客 - 私のサンプル エンティティ
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.Table;
@Entity
@Table(name = "Customers")
public class Customer{
@Id
@GeneratedValue(strategy=GenerationType.IDENTITY)
@Column(name = "ID_CUSTOMER")
private Long id;
@Column(name = "dbfirstname")
private String firstName;
@Column(name = "dbname")
private String lastName;
public Long getId(){
return id;
}
public String getFirstName(){
return firstName;
}
public void setFirstName(String firstName){
this.firstName = firstName;
}
public String getLastName(){
return lastName;
}
public void setLastName(String lastName){
this.lastName = lastName;
}
}
私は、WebSphere でクラスパスの地獄から抜け出しました (くそー、なんて大混乱した製品でしょう) そして今、私はここにいます。誰かがこれで私を助けてくれることを願っています。
正確に何がうまくいかないかの基本的な説明と、おそらくスプリングの自動配線された注入機能の理解を深めることができれば素晴らしいでしょう。春のドキュメントを読みましたが、実を言うと、何かを構成する方法が非常に多く、構成スタイルの 1 つを選択するときに何が本当に必要なのかがよくわかりません。
編集
プロジェクトを更新しようとしても、まだエラーが発生します。ここで要求されたように、もう少し詳細 (トレース):
Exception created : org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'customerService': Injection of autowired dependencies failed; nested exception is org.springframework.beans.factory.BeanCreationException: Could not autowire field: private model.repositories.CustomerRepository model.service.CustomerService.repository; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'customerRepository': FactoryBean threw exception on object creation; nested exception is java.lang.NullPointerException
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:287)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1106)
[...]
at com.ibm.ws.http.HttpConnection.run(HttpConnection.java:522)
at com.ibm.ws.util.ThreadPool$Worker.run(ThreadPool.java:1563)
Caused by: org.springframework.beans.factory.BeanCreationException: Could not autowire field: private model.repositories.CustomerRepository model.service.CustomerService.repository; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'customerRepository': FactoryBean threw exception on object creation; nested exception is java.lang.NullPointerException
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:506)
at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:87)
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:284)
... 96 more
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'customerRepository': FactoryBean threw exception on object creation; nested exception is java.lang.NullPointerException
at org.springframework.beans.factory.support.FactoryBeanRegistrySupport.doGetObjectFromFactoryBean(FactoryBeanRegistrySupport.java:149)
at org.springframework.beans.factory.support.FactoryBeanRegistrySupport.getObjectFromFactoryBean(FactoryBeanRegistrySupport.java:102)
at org.springframework.beans.factory.support.AbstractBeanFactory.getObjectForBeanInstance(AbstractBeanFactory.java:1442)
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:248)
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:193)
at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:848)
at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:790)
at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:707)
at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:478)
... 98 more
Caused by: java.lang.NullPointerException
at org.hibernate.engine.transaction.internal.jta.JtaStatusHelper.getStatus(JtaStatusHelper.java:73)
at org.hibernate.engine.transaction.internal.jta.JtaStatusHelper.isActive(JtaStatusHelper.java:115)
at org.hibernate.engine.transaction.internal.jta.CMTTransaction.join(CMTTransaction.java:149)
at org.hibernate.ejb.AbstractEntityManagerImpl.joinTransaction(AbstractEntityManagerImpl.java:1215)
at org.hibernate.ejb.AbstractEntityManagerImpl.postInit(AbstractEntityManagerImpl.java:177)
at org.hibernate.ejb.EntityManagerImpl.<init>(EntityManagerImpl.java:89)
at org.hibernate.ejb.EntityManagerFactoryImpl.createEntityManager(EntityManagerFactoryImpl.java:179)
at org.hibernate.ejb.EntityManagerFactoryImpl.createEntityManager(EntityManagerFactoryImpl.java:174)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:48)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:600)
at org.springframework.orm.jpa.AbstractEntityManagerFactoryBean.invokeProxyMethod(AbstractEntityManagerFactoryBean.java:376)
at org.springframework.orm.jpa.AbstractEntityManagerFactoryBean$ManagedEntityManagerFactoryInvocationHandler.invoke(AbstractEntityManagerFactoryBean.java:517)
at $Proxy325.createEntityManager(Unknown Source)
at org.springframework.orm.jpa.SharedEntityManagerCreator$SharedEntityManagerInvocationHandler.invoke(SharedEntityManagerCreator.java:234)
at $Proxy328.createNamedQuery(Unknown Source)
at org.springframework.data.jpa.repository.query.NamedQuery.<init>(NamedQuery.java:74)
at org.springframework.data.jpa.repository.query.NamedQuery.lookupFrom(NamedQuery.java:96)
at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$DeclaredQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:128)
at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$CreateIfNotFoundQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:162)
at org.springframework.data.jpa.repository.query.JpaQueryLookupStrategy$AbstractQueryLookupStrategy.resolveQuery(JpaQueryLookupStrategy.java:71)
at org.springframework.data.repository.core.support.RepositoryFactorySupport$QueryExecutorMethodInterceptor.<init>(RepositoryFactorySupport.java:303)
at org.springframework.data.repository.core.support.RepositoryFactorySupport.getRepository(RepositoryFactorySupport.java:157)
at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.getObject(RepositoryFactoryBeanSupport.java:120)
at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.getObject(RepositoryFactoryBeanSupport.java:39)
at org.springframework.beans.factory.support.FactoryBeanRegistrySupport.doGetObjectFromFactoryBean(FactoryBeanRegistrySupport.java:142)
編集#2 は、applicationContext.xmlを完成させます(進行中の議論に基づいて行った変更を含む)が要求に応じて追加されました
<context:annotation-config />
<jpa:repositories base-package="model.repositories" />
<context:component-scan base-package="model,model.repositories,model.service,controller" />
<bean class="model.service.CustomerService"/>
<bean class="model.service.OrderService"/>
<bean class="model.repositories.CustomerRepository"/>
<bean class="model.repositories.OrderRepository"/>
<bean id="myExceptionTranslator" class="org.springframework.orm.hibernate4.HibernateExceptionTranslator" />
<jee:jndi-lookup id="dataSource" jndi-name="jdbc/mydata"
resource-ref="true" cache="true" />
<bean id="pum"
class="org.springframework.orm.jpa.persistenceunit.DefaultPersistenceUnitManager">
<property name="persistenceXmlLocations">
<list>
<value>classpath*:META-INF/OverridePersistence.xml</value>
</list>
</property>
<property name="defaultDataSource" ref="dataSource" />
</bean>
<bean id="entityManagerFactory"
class="org.springframework.orm.jpa.LocalContainerEntityManagerFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="jpaVendorAdapter">
<bean class="org.springframework.orm.jpa.vendor.HibernateJpaVendorAdapter">
<property name="generateDdl" value="true" />
<property name="database" value="MYSQL" />
</bean>
</property>
<property name="persistenceUnitManager" ref="pum" />
<property name="persistenceUnitName" value="default" />
</bean>
<bean id="mySessionFactory"
class="org.springframework.orm.hibernate4.LocalSessionFactoryBean">
<property name="dataSource" ref="dataSource" />
<property name="packagesToScan" value="model"/>
<property name="hibernateProperties">
<value>hibernate.dialect=org.hibernate.dialect.MySQLDialect</value>
</property>
</bean>
<bean id="transactionManager"
class="org.springframework.orm.hibernate4.HibernateTransactionManager">
<property name="entityManagerFactory" ref="entityManagerFactory"/>
<property name="sessionFactory" ref="mySessionFactory" />
</bean>
<tx:annotation-driven />
<bean class="org.springframework.orm.jpa.support.PersistenceAnnotationBeanPostProcessor" />