如何在Spring Data中将OrderBy与findAll一起使用


287

我正在使用spring数据,我的DAO看起来像

public interface StudentDAO extends JpaRepository<StudentEntity, Integer> {
    public findAllOrderByIdAsc();   // I want to use some thing like this
}

在上面的代码中,注释行显示了我的意图。Spring Data是否可以提供内置功能来使用这种方法来按ASC / DESC查找某一列的所有记录顺序?

Answers:


655
public interface StudentDAO extends JpaRepository<StudentEntity, Integer> {
    public List<StudentEntity> findAllByOrderByIdAsc();
}

上面的代码应该可以工作。我正在使用类似的东西:

public List<Pilot> findTop10ByOrderByLevelDesc();

它返回最高级别的10行。

重要提示: 由于有人告诉我很容易错过此答案的关键点,因此需要澄清一下:

findAllByOrderByIdAsc(); // don't miss "by"
       ^

4
为了使方法签名能够按预期与Spring Data JPA一起使用,应包括“ all”关键字,如下所示:List<StudentEntity> findAllByOrderByIdAsc();。添加返回类型并删除多余的公共修饰符也是一个好主意;)
HåvardGeithus 15-4-20

1
我同意public是多余的,但是它可以使事情变得清晰,以防其他人必须处理您的代码。您永远都不会知道:PI在作者代码中没有更改方法名称以外的任何内容,因为这不是问题所在,而且如果有人不知道应该在那里,希望他们会学到新东西。此外,在下面的示例中,这样他们就不必搜索上帝知道的位置了,但是如果您坚持要的话,就这样:)添加了'all'关键字。谢谢。
西科

73
请注意,关键字By前的OrderBy所有内容均会有所不同。
Stefan Haberl,2015年

5
仍然不明白为什么需要By在的前面添加额外的内容OrderBy。该文档没有透露这一点
Xtreme Biker

3
@XtremeBiker从您提供的文档链接中:“但是,第一个By用作分隔符,以指示实际标准的开始。” 此外,如果您向下滚动到“ 3.4.5。限制查询结果”部分,则实际上存在这样的示例,但未进行说明。
西科

54

AFAIK,我认为使用直接方法命名查询是不可能的。但是,您可以使用类使用内置的排序机制Sort。存储库中有一个findAll(Sort)您可以将实例传递Sort给的方法。例如:

import org.springframework.data.domain.Sort;

@Repository
public class StudentServiceImpl implements StudentService {
    @Autowired
    private StudentDAO studentDao;

    @Override
    public List<Student> findAll() {
        return studentDao.findAll(sortByIdAsc());
    }

    private Sort sortByIdAsc() {
        return new Sort(Sort.Direction.ASC, "id");
    }
} 

确实可以使用findAllByOrderByIdAsc()来实现,如下面Sikor的答案中所述 ……@Prashant确实应该是正确的答案
Samuel Parsonage

如果要使存储库更整洁,可以在服务层中进行排序的另一种方法。请记住结果的大小!
dkanejs 2016年

2
findAll()类型中的方法CrudRepository<>不适用于参数(排序)
Thiago Pereira

5
@ThiagoPereira JpaRepository<>如果您想使用上面的示例,则应该扩展。
Waleed Abdalmajeed



3

是的,您可以在Spring Data中使用查询方法进行排序。

例如:使用id字段的值是升序还是降序。

码:

  public interface StudentDAO extends JpaRepository<StudentEntity, Integer> {
    public findAllByOrderByIdAsc();   
}

替代解决方案:

    @Repository
public class StudentServiceImpl implements StudentService {
    @Autowired
    private StudentDAO studentDao;

    @Override
    public List<Student> findAll() {
        return studentDao.findAll(orderByIdAsc());
    }
private Sort orderByIdAsc() {
    return new Sort(Sort.Direction.ASC, "id")
                .and(new Sort(Sort.Direction.ASC, "name"));
}
}

Spring数据排序:排序


3

我在此示例中尝试向您展示一个完整的示例,以个性化您的OrderBy排序

 import java.util.List;
 import org.springframework.data.domain.Page;
 import org.springframework.data.domain.Sort;
 import org.springframework.data.jpa.repository.*;
 import org.springframework.data.repository.query.Param;
 import org.springframework.stereotype.Repository;
 import org.springframework.data.domain.Sort;
 /**
 * Spring Data  repository for the User entity.
 */
 @SuppressWarnings("unused")
 @Repository
 public interface UserRepository extends JpaRepository<User, Long> {
 List <User> findAllWithCustomOrderBy(Sort sort);
 }

您将使用以下示例:一种用于动态构建Sort实例的对象的方法:

import org.springframework.data.domain.Sort;
public class SampleOrderBySpring{
 Sort dynamicOrderBySort = createSort();
     public static void main( String[] args )
     {
       System.out.println("default sort \"firstName\",\"name\",\"age\",\"size\" ");
       Sort defaultSort = createStaticSort();
       System.out.println(userRepository.findAllWithCustomOrderBy(defaultSort ));


       String[] orderBySortedArray = {"name", "firstName"};
       System.out.println("default sort ,\"name\",\"firstName\" ");
       Sort dynamicSort = createDynamicSort(orderBySortedArray );
       System.out.println(userRepository.findAllWithCustomOrderBy(dynamicSort ));
      }
      public Sort createDynamicSort(String[] arrayOrdre) {
        return  Sort.by(arrayOrdre);
        }

   public Sort createStaticSort() {
        String[] arrayOrdre  ={"firstName","name","age","size");
        return  Sort.by(arrayOrdre);
        }
}

0

结合以上所有答案,您可以使用BaseEntity编写可重用的代码:

@Data
@NoArgsConstructor
@MappedSuperclass
public abstract class BaseEntity {

  @Transient
  public static final Sort SORT_BY_CREATED_AT_DESC = 
                        Sort.by(Sort.Direction.DESC, "createdAt");

  @Id
  private Long id;
  private LocalDateTime createdAt;
  private LocalDateTime updatedAt;

  @PrePersist
  void prePersist() {
    this.createdAt = LocalDateTime.now();
  }

  @PreUpdate
  void preUpdate() {
    this.updatedAt = LocalDateTime.now();
  }
}

DAO对象重载了findAll方法-基本上,仍然使用 findAll()

public interface StudentDAO extends CrudRepository<StudentEntity, Long> {

  Iterable<StudentEntity> findAll(Sort sort);

}

StudentEntityBaseEntity包含可重复字段的扩展(也许您也想按ID排序)

@Getter
@Setter
@FieldDefaults(level = AccessLevel.PRIVATE)
@Entity
class StudentEntity extends BaseEntity {

  String firstName;
  String surname;

}

最后,其服务和用法SORT_BY_CREATED_AT_DESC可能不仅会在中使用StudentService

@Service
class StudentService {

  @Autowired
  StudentDAO studentDao;

  Iterable<StudentEntity> findStudents() {
    return this.studentDao.findAll(SORT_BY_CREATED_AT_DESC);
  }
}
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.