IllegalStateException с использованием CriteriaBuilder для получения списка в Java - PullRequest
0 голосов
/ 17 декабря 2018

Подводя итог, у меня есть 3 сущности, основной из которых является сущность с именем "Rac".Содержит список «RacNatureza», который содержит атрибут «Natureza».

Rac

    @Entity
    @Table(name = "rac")
    public class Rac {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    private Long idRac;    

    @OneToMany(mappedBy = "rac", cascade = {CascadeType.ALL}, orphanRemoval = true)
    @JsonManagedReference //para evitar recursão infinita do JSON
    private List<RacNatureza> racNaturezas;

    //...getters and setters ok
}

RacNatureza

@Entity
@Table(name = "rac_natureza")
public class RacNatureza implements Serializable {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id_rac_natureza")
    private Long idRacNatureza;

    @ManyToOne
    @JsonBackReference //coloquei para evitar a recursao infinita de JSON
    @JoinColumn(name="id_rac")
    private Rac rac;

    @ManyToOne
    @JoinColumn(name="id_natureza")
    private Natureza natureza;

    @Column(name = "principal")
    private Boolean principal;
}

Natureza

@Entity
@Table(name = "natureza")
public class Natureza {

    @Id
    @GeneratedValue(strategy = GenerationType.IDENTITY)
    @Column(name = "id_natureza")
    private Integer idNatureza;
    private String descricao;

    @OneToMany(mappedBy = "natureza", fetch = FetchType.EAGER, orphanRemoval = true)
    @JsonIgnore
    private List<RacNatureza> racNatureza;
}

Я пытаюсь разработать поиск с использованием фильтров, в этом случае пользователь выбирает список «Natureza», а затем система должна показать, какой «Rac» содержит Natureza, который был выбран пользователем.Для этого я попытался реализовать с использованием Entitymanager и Criteriabuilder.

Я пытался написать выражение, как это, но не работает (я не использую метамодель):

@PersistenceContext
private EntityManager entityManager;

@Override
public List<Rac> filtrar(RacFilter racFilter) {
    CriteriaBuilder builder = entityManager.getCriteriaBuilder();
    CriteriaQuery<Rac> criteria = builder.createQuery(Rac.class);
    Root<Rac> root = criteria.from(Rac.class);

    Predicate[] predicates = criarRestricoes(racFilter, builder, root);
    criteria.where(predicates);

    TypedQuery<Rac> query = entityManager.createQuery(criteria);
    return query.getResultList();

}

@Override
public Predicate[] criarRestricoes(RacFilter racFilter, CriteriaBuilder builder, Root<Rac> root) {
    List<Predicate> predicates = new ArrayList<>();
    if (racFilter.getNaturezas() != null) {
        predicates.add(
                builder.equal(root.<List<RacNatureza>>get("racNaturezas").<Natureza>get("natureza"), racFilter.getNaturezas()) );
    }   
    return predicates.toArray(new Predicate[predicates.size()]);
}

Итак, используя этот код выше, я получилследующая ошибка: Причина: java.lang.IllegalStateException: незаконная попытка разыменования источника пути [null.racNaturezas] базового типа

Я считаю, что ошибка в этой строке, но ядействительно не знаю как это исправить:

    predicates.add(
            builder.equal(root.<List<RacNatureza>>get("racNaturezas").<Natureza>get("natureza"), racFilter.getNaturezas()) );
}   

1 Ответ

0 голосов
/ 10 апреля 2019

Заменить root.get("racNaturezas") на root.join("racNaturezas")

Пожалуйста, не спрашивайте меня, почему мы не можем использовать get

...