Spring Данные - игнорировать параметр, если он имеет нулевое значение

Я хочу иметь интерфейс репозитория данных spring, который принимает два параметра. Есть ли способ сделать это следующим образом?

MyObject findByParameterOneAndParameterTwo( String parameterOne, String parameterTwo);

Если оба параметра имеют значение, я бы хотел, чтобы он вел себя нормально и выполнял "И" для обоих значений.

Если, например, второй параметр имеет значение null, он будет искать только параметр ParameterOne

Любые предложения?

Ответ 1

Я не уверен, что это возможно с именами методов репозитория, но вы можете использовать @Query как

(:parameterOne is null or parameter1 = :parameterOne) and (:parameterTwo is null or parameter2 = :parameterTwo)

Ответ 2

В настоящее время это невозможно в Spring-data-jpa.

На этот счет есть билет JIRA который все еще расследуется командой Spring.

enter image description here

Однако, если вы хотите обойти это, вы можете воспользоваться простым примером запроса критериев.

Ответ 3

Одним из решений, которое здесь отсутствует, является функция Spring Data JPA Query By Example, использующая ExampleMatcher#ignoreNullValues, которая создана именно для решения этой проблемы. Пользовательский запрос и построитель запросов не нужны.

Этот Spring Data запрос:

ExampleMatcher matcher = ExampleMatcher.matching().withIgnoreNullValues();
Example<MyObject> exampleQuery = Example.of(new MyObject("foo", null), matcher);
List<MyObject> results = repository.findAll(exampleQuery);

Выдает запрос, который выглядит следующим образом:

select * 
from myObject 
where parameter1 = "foo"

Пока следующее:

ExampleMatcher matcher = ExampleMatcher.matching().withIgnoreNullValues();
Example<MyObject> exampleQuery = Example.of(new MyObject("foo", "bar"), matcher);
List<MyObject> results = repository.findAll(exampleQuery);

Урожайность:

select * 
from myObject 
where parameter1 = "foo"
and parameter2 = "bar"

Очень круто!

Примечание. Единственное, что вам нужно сделать с интерфейсом Repository - это добавить интерфейс QueryByExample. Вы можете сделать это, либо напрямую QueryByExample интерфейс QueryByExample, либо JpaRepository через JpaRepository:

public interface MyObjectRepository extends JpaRepository<MyObject, Long> {}

Ответ 4

Я новичок в пространстве Spring/JPA,

используйте "Запрос по примеру"

я использую (в seviceImp), все ниже аргументы являются необязательными/зависит от выбора пользователя

'
  .
    if (!firstName.isEmpty() ) {
    staff.setFirstName(firstName);
    }



    if (!lastName.isEmpty() ) {
    staff.setLastName(lastName);
    }

    if (!ptAadhar.isEmpty() ) {
        patient.setPtAadhar(ptAadhar);
    }

    if (!Cell.isEmpty() ) {
        staff.setCell(Cell);
    }


      Example<StaffEntity> example = Example.of(staff);  

      List<StaffEntity> staffList =staffRepository.findAll(example);
       .

Ответ 5

Попробуйте это,

      @Query(value = "SELECT pr FROM ABCTable pr " +
        "WHERE((pr.parameterOne = :parameterOne) or (pr.parameterOne = null and :parameterOne = null)) and 
        ((pr.parameterTwo = :parameterTwo) or (pr.parameterTwo = null and :parameterTwo = null)) ")
      List<PaymentRequest> getSomething (@Param("parameterOne") String parameterOne,
                                             @Param("parameterTwo") String parameterTwo);

Ответ 6

Я не уверен, возможно ли использование Repo в качестве отдельного класса, но вы можете использовать запрос добавления StringBuilder с параметром параметра. Это определенно будет работать

 StringBuilder queryBuilder = new StringBuilder();
    queryBuilder.append("select p.name from personDemographic p "); 
    Boolean flag = true;
    if(parameterOne != null){
      if(flag){
          queryBuilder.append("where condition...");
            flag=false;
        } 
      }
    if(parameterOne != null){
    if(flag){
     queryBuilder.append("where condition...");
     flag = false;
    }else{
      queryBuilder.append("and condition...");
    }
   Query query = entityManager.createQuery(queryBuilder.toString());