2015-08-19 33 views
7

使用Spring Data nad Querydsl我們可以聲明存儲庫接口並跳過實現類。一些具有特定名稱或使用@Query註釋的方法,就這些。在Spring數據中使用Querydsl的最佳實踐

但有時我想使用JPAQuery,並通過自己定義方法的身體,讓我們說

@Repository 
public class MyRepositoryImpl implements MyRepository { 

    @PersistenceContext 
    private EntityManager em; 

    @Override 
    public List<Tuple> someMethod(String arg) { 
     JPAQuery query = new JPAQuery(em); 
     ... 
    } 

但這樣一來我就必須實現其他MyRepository接口方法,其遺址所有的Spring Data的優勢!

我可以看到兩個選項:

  • 每聲明每個庫的另一個接口,然後正常地執行它(其中的接口數量增加一倍)
  • 進樣的EntityManager成@服務類,並實現我的自定義方法有

我更喜歡選項#2,但據我所知,在@Service類中,我們應該只調用存儲庫方法,所以它也不是一個完美的解決方案。

那麼程序員如何處理它呢?

+1

我面臨同樣的問題,目前我選擇了服務層來使用'JPQLQuery' – Paizo

回答

8

您不應該實現實際的Spring數據存儲庫,而是必須聲明另一個可以放置自定義方法的自定義接口。

比方說,你有一個MyRepository,定義爲

@Repository 
public interface MyRepository extends JpaRepository<Tuple, Long> {} 

現在,你想添加自定義findTuplesByMyArg()爲目的的緣故,你需要創建自定義庫界面

public interface MyRepositoryCustom { 
    List<Tuple> findTuplesByMyArg(String myArg); 
} 

隨後來到定製界面的實現

public class MyRepositoryImpl implements MyRepositoryCustom { 
    @PersistenceContext 
    private EntityManager em; 

    @Override 
    public List<Tuple> findTuplesByMyArg(String myArg) { 
     JPAQuery query = new JPAQuery(em); 
     ... 
    }  
} 

而我們需要改變MyRepository聲明,所以它擴展的自定義庫,使

@Repository 
public interface MyRepository extends JpaRepository<Tuple, Long>, MyRepositoryCustom {} 

而且你可以輕鬆地將findTuplesByMyArg()通過注入MyRepository訪問,例如

@Service 
public class MyService { 
    @Autowired 
    private MyRepository myRepository; 

    public List<Tuple> retrieveTuples(String myArg) { 
     return myRepository.findTuplesByMyArg(myArg); 
    } 
} 

注重名稱在這裏重要的(你必須回購實施Impl後綴默認CONFIGS)。

你可以找到所有需要的信息here

1

我建議未成年整改上面的答案,它試圖用JPAQueryFactory。使用提供的工廠類是很好的。

public class MyRepositoryImpl implements MyRepositoryCustom { 
@Autowired 
private JPAQueryFactory factory; 

@Override 
public List<Tuple> findTuplesByMyArg(String myArg) { 
    JPAQuery query = factory.query(); 
    ... 
}} 

@Configuration 
public class Config { 

@Autowired 
private EntityManager em; 

@Bean 
public JPAQueryFactory jpaQueryFactory() { 
     return new JPAQueryFactory(em); 
} 

}