2017-09-13 57 views
0

我想從多個表中使用spring JPA檢索報表。 所以我將java.lang.Object作爲實體傳遞給JpaRepository。 我已經試過類似如何在spring中編寫GenericRepository jpa

案例1:

@NoRepositoryBean 
public interface ObjectRepository extends JpaRepository<Object, Long> { 

    @Query(value = "SELECT new InOutReport(it.customer_name 'partyName', if(it.in_out_action =0,'SALE','PURCHASE') 'transactionType', it.invoice_no 'invoiceNo', im.product_name 'productName' ,it.qty 'qty',it.handed_over_to_or_by 'handedOverToOrBy', it.date 'date')" 
      + " FROM inventory_transaction it, inventory_master im WHERE it.inventory_id = im.inventory_id") 
    List<InOutReport> getInOutReport(); 
} 

我會得到錯誤,如

APPLICATION FAILED TO START 
*************************** 

Description: 

Field objectRepository in com.test.service.ReportServiceImpl required a bean of type 'com.test.repository.ObjectRepository' that could not be found. 


Action: 

Consider defining a bean of type 'com.test.repository.ObjectRepository' in your configuration. 

案例2: 如果定義@Repository註解

@Repository 
public interface ObjectRepository{ 
    ... 
} 

我會得到錯誤,如

Caused by: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'reportServiceImpl': Unsatisfied dependency expressed through field 'objectRepository'; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'objectRepository': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Not a managed type: class java.lang.Object 
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:588) 
    at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:88) 
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessPropertyValues(AutowiredAnnotationBeanPostProcessor.java:366) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1264) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:553) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:483) 
    at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306) 
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) 
    at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302) 
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202) 
    at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:208) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1138) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1066) 
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:585) 
    ... 24 common frames omitted 
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'objectRepository': Invocation of init method failed; nested exception is java.lang.IllegalArgumentException: Not a managed type: class java.lang.Object 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1628) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:555) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:483) 
    at org.springframework.beans.factory.support.AbstractBeanFactory$1.getObject(AbstractBeanFactory.java:306) 
    at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:230) 
    at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:302) 
    at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202) 
    at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:208) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1138) 
    at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1066) 
    at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:585) 
    ... 37 common frames omitted 
Caused by: java.lang.IllegalArgumentException: Not a managed type: class java.lang.Object 
    at org.hibernate.jpa.internal.metamodel.MetamodelImpl.managedType(MetamodelImpl.java:210) 
    at org.springframework.data.jpa.repository.support.JpaMetamodelEntityInformation.<init>(JpaMetamodelEntityInformation.java:70) 
    at org.springframework.data.jpa.repository.support.JpaEntityInformationSupport.getEntityInformation(JpaEntityInformationSupport.java:68) 
    at org.springframework.data.jpa.repository.support.JpaRepositoryFactory.getEntityInformation(JpaRepositoryFactory.java:153) 
    at org.springframework.data.jpa.repository.support.JpaRepositoryFactory.getTargetRepository(JpaRepositoryFactory.java:100) 
    at org.springframework.data.jpa.repository.support.JpaRepositoryFactory.getTargetRepository(JpaRepositoryFactory.java:82) 
    at org.springframework.data.repository.core.support.RepositoryFactorySupport.getRepository(RepositoryFactorySupport.java:199) 
    at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.initAndReturn(RepositoryFactoryBeanSupport.java:277) 
    at org.springframework.data.repository.core.support.RepositoryFactoryBeanSupport.afterPropertiesSet(RepositoryFactoryBeanSupport.java:263) 
    at org.springframework.data.jpa.repository.support.JpaRepositoryFactoryBean.afterPropertiesSet(JpaRepositoryFactoryBean.java:101) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.invokeInitMethods(AbstractAutowireCapableBeanFactory.java:1687) 
    at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.initializeBean(AbstractAutowireCapableBeanFactory.java:1624) 
    ... 47 common frames omitted 

請建議我在哪裏做錯了。

回答

1

這個錯誤意味着Object不被視爲一個實體:java.lang.IllegalArgumentException異常:

通過引起了不託管類型: 類java.lang

它是這樣的:Object不是一個實體。
如果你想用同一個Spring存儲庫處理所有的實體,你應該引入一個基類並使所有的報表類擴展這個基類。

然後使用這個基類參數你的資料庫:

public interface MyEntityRepository extends JpaRepository<MyEntity, Long> { 

。當然,這是有道理的,如果你的所有報表類具有共同的結構。否則,你將不得不做一些向下轉換,你會完成一個脆弱的,不可讀的代碼。

+0

但是如果MyEntity沒有映射到任何表中,該怎麼辦?它不同表格的組合。在那種情況下,我該如何繼續? – Vish

+0

返回一個特定的類而不是一個實體是JPA的一個非常特殊的情況:它只允許檢索並且不返回實體。因此,通過返回它,您可以通過某種方式禁用JPA功能(對實體的操作不再可用)。我不認爲Spring JpaRepository解決了這個問題。我認爲你應該創建一個註釋了@ @Service的自定義類,並明確使用'entityManager'來滿足你的需求:一個處理所有報表的通用類。 – davidxxx

+0

並請編輯您的問題與此要求。它很重要。 – davidxxx

0

您可以從多個表中創建數據庫視圖,然後爲其創建實體。如果您僅將它用於報告目的,這應該可以解決您的問題。 但你不能更新同樣的東西。

@Entity 
@Table(name="VW_reports") 
@NamedQuery(name="ViewReports.findAll", query="SELECT v FROM ViewReports v") 
public class ViewReports { 
} 
+0

您能否詳細說明一下? 1.什麼是VW_reports? 2.如果我在數據庫中定義視圖,那麼爲什麼你再次將查詢寫爲命名查詢? – Vish

+0

vw_reports將是您的數據庫表視圖的實體表示形式,您可以忽略namedQuery .. –

相關問題