Java 使用枚举列表作为参数的IN关键字的Spring数据查询方法
我正在使用一个SpringDataJPA(4.3.5)存储库和一个查询方法,该方法使用IN关键字子句,并将Java 使用枚举列表作为参数的IN关键字的Spring数据查询方法,java,spring,spring-data,Java,Spring,Spring Data,我正在使用一个SpringDataJPA(4.3.5)存储库和一个查询方法,该方法使用IN关键字子句,并将列表字段作为参数。问题是它没有像我预期的那样工作 给定如下实体: @Entity @Table(name = "R_REPRESENTACIO") public class Representacio { @Enumerated(EnumType.STRING) private Estat estat; ... //getters and sette
列表
字段作为参数。问题是它没有像我预期的那样工作
给定如下实体:
@Entity
@Table(name = "R_REPRESENTACIO")
public class Representacio {
@Enumerated(EnumType.STRING)
private Estat estat;
...
//getters and setters
...
}
使用该SQL声明:
CREATE TABLE R_REPRESENTACIO (
UUID NUMBER(19) NOT NULL,
...
ESTAT VARCHAR2(255) NULL,
...
);
Estat
是一个枚举类,类似于:
public enum Estat {
VALIDA,
PENDENT_VALIDACIO,
PENDENT_DOCUMENTACIO,
...
}
和JPA存储库,如:
public interface RepresentacioRepository extends JpaRepository<Representacio, Long> {
List<Representacio> findAllByEstatIn(List<Estat> estats);
}
不会引发任何SQL异常,并且不会返回任何结果。
但这应该返回1个结果,因为此(等效)SQL返回:
SELECT count(*) FROM R_REPRESENTACIO WHERE ESTAT IN ('VALIDA','PENDENT_DOCUMENTACIO','PENDENT_VALIDACIO');
COUNT(*)
----------
1
我能看到的唯一区别是如何在“”之间包装IN子句参数(该列是一个VARCHAR)
我不知道为什么从JPA存储库生成的SQL没有返回结果。
(我还尝试了findallbystatisin(List estats)
,返回了相同的零结果)
有什么建议/解释吗
PS:变通(不满意)使用
列出findallbyestatrestater(Estat-Estat、Estat-estat2、Estat-estat3);
但这在很多方面都是丑陋和错误的…我建议使用类型为
List
的参数,并添加转换器String->Enum
,这样Spring就可以转换它了。因此,基本上:
List findByEstatIn(List estats)代码>
@配置
公共类转换器配置扩展了RepositoryRestConfigurerAdapter{
@自动连线
私人房地产转换人房地产转换人;
@凌驾
公共void配置转换服务(ConfigurableConversionService转换服务){
conversionService.addConverter(EstatConverter);
super.configureConversionService(conversionService);
}
3.
@组件
公共类EstatConverter实现转换器{
@凌驾
公共资产转换(字符串源){
返回Estat.fromString(源);
}
}
我不知道这是否可行,但我记得我做过类似的事情,只是在MongoDB中。如果您尝试过,请告诉我。使用spring数据JPA和JPQL非常简单:
@Repository
public interface RepresentacioRepository extends JpaRepository<Representacio, Long> {
@Query("select r from Representacio r where r.estat in :estat2")
List<Representacio> findByEnumEstat(@Param("estat2") List<Estat> estatList);
}
@存储库
公共接口RepresentationRepository扩展了JpaRepository{
@查询(“从Representacio r中选择r,其中r.estat in:estat2”)
List findByEnumEstat(@Param(“estat2”)List estatList);
}
如您所述,@Enumerated(EnumType.STRING)
列是varchar,但您的参数是一个枚举列表。您是否尝试过使用字符串列表?是的,尝试了类似FindAllByestin(List estats)的存储库方法,并运行repo.FindAllByestin(Arrays.asList(“VALIDA”,“PENDENT\u VALIDACIO”…)但是抛出java.lang.ClassCastException:java.lang.String不能被强制转换为java.lang.Enum您是否尝试过自己编写一个查询?@query(“从Representacio r中选择r,其中r.estat位于:estats”)
如果您跳过“全部”并使用列表findByEstatIn(列表estat)会怎么样
?@mrkernelpanic我希望了解IN子句的工作原理和方式,并尽可能避免编写sql,但在这种情况下,您的解决方案很简单,正如我所期望的那样工作。您的解决方案很好!我喜欢您的aproach,但我使用的不是REST存储库,而是JpaRepository,无法使用RepositoryRestConfigurerAdapter类。我一直在寻找或者JpaReposotory的类似解决方案,但我不知道如何…我想知道IN子句为什么或如何在具有枚举列表的查询方法中工作,但正如@mrkernelpanic在问题中所评论的,此解决方案解决了muy用例
SELECT count(*) FROM R_REPRESENTACIO WHERE ESTAT IN ('VALIDA','PENDENT_DOCUMENTACIO','PENDENT_VALIDACIO');
COUNT(*)
----------
1
List<Representacio> findAllByEstatOrEstatOrEstat(Estat estat, Estat estat2, Estat estat3);
@Repository
public interface RepresentacioRepository extends JpaRepository<Representacio, Long> {
@Query("select r from Representacio r where r.estat in :estat2")
List<Representacio> findByEnumEstat(@Param("estat2") List<Estat> estatList);
}