2017-04-11 89 views
2

我想使用Spring JPA的投影从查询结果中筛选出不必要的数据。但是,我有多个预测需要在相同的接口方法上使用。Spring JPA:在同一查询接口上使用多个投影

问题是,我试图用不同的返回对象从同一个方法中查询数据,但java不允许这样做。

该查询是由JPA根据方法名称自动生成的,因此我无法更改方法名称。

是否有替代方案,比创建一个新的接口等,因为我认为这是一个麻烦和不必要的

这里是一个示例代码,我试图做的。

Auto-Generated Query

public interface UserRepository extends CrudRepository<UserAccount, Long> { 

    AuthenticateProjection getByUsername(String username); 

    UserDetailsProjection getByUsername(String username); 

} 

Projections

public interface AuthenticateProjection { 

    @Value("#{target.username}") 
    String getUsername(); 

    @Value("#{target.credentail.token}") 
    String getHashPassword(); 
} 

public interface UserDetailsProjection { 

    @Value("#{target.username}") 
    String getUsername(); 

    @Value("#{target.firstname}") 
    String getFirstName(); 

    @Value("#{target.lastname}") 
    String getLastName(); 
} 
+0

调用查询方法 - 这是从控制器返回,或内部使用? – chrylis

+0

@chrylis它将返回到控制器 – XPLOT1ON

回答

2

所以我设法弄清楚如何使用多个投影使用单个查询。

<T> T getByUsername(String username, Class<T> projection) 

这允许方法调用方指定要应用于查询的投影类型。

为了进一步改善这个,所以不太容易出错,我做了一个空白的接口,为了能够将类插入到参数中,投影将不得不扩展。

public interface JPAProjection { 
} 

public interface UserRepository extends CrudRepository<UserAccount, Long> { 
    <T extends JPAProjection > T getByUsername(String username, Class<? extends JPAProjection> projection); 
} 

Projection Interface

public interface UserDetailsProjection extends JPAProjection{ 
    @Value("#{target.username}") 
    String getUsername(); 

    @Value("#{target.firstname}") 
    String getFirstname(); 

    @Value("#{target.lastname}") 
    String getLastname(); 
} 

然后,我可以问:你为什么要“过滤器”的信息,通过

getByUsername("...", UserDetailsProjection.class) 
+0

我试图使用相同的解决方案,但它不适用于我。在Eclipse控制台中,我看到一个错误:'由...引起:org.hibernate.hql.internal.ast.QuerySyntaxException:意外的令牌:从第1行第9列[从com.app.company.domain.organization.Organization中选择generatedAlias0 where generatedAlias0.deletedAt is null]'。看看“select”语句:没有任何列。也许你有同样的问题?看来版本库没有收到正确的投影类型.....任何想法?非常感谢! –

+0

嗯这很奇怪。我没有任何问题。你介意附上你的impl吗? Pastebin可能? @AndreaBevilacqua – XPLOT1ON