Search code examples
javahibernatenetbeanscriteriahibernate-criteria

Criteria: How to get childs without parents


I have a little problem with Criteria and Hibernate on Netbeans.

The solutions that can serve me are several: using the metamodel in Netbeans (it is the solution to all my problems, but console often spits an error saying that it does not find the source), or the code needed to do the query.

The situation is the following: I have a parent entity called Grado, and a child entity called Materia. The relationship is one to many. A Grado can have several Materias: English, Mathematics, Physics, Ethics ...

I need to do a query, or several, to get a list of the materias without assigning a parent. The equivalent in SQL that I am trying to get is: SELECT * FROM Materia where id not in (select id from Materia m join grado_materia g on m.id = g.materias_id);

Grado parent entity:

@Entity
public class Grado implements Serializable {

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

    @Basic
    private String nombre;

    @OneToMany(orphanRemoval = true)
    private List<Materia> materias;

    //getters and setters
}

Materia child entity

@Entity
public class Materia implements Serializable {

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

    @Basic(optional = false)
    private String nombre;

    //getters and setters
}

Hibernate generates the following relations grado -> grado_materia <- materia

Edit To complete the solution provided by @Spiderman to the problem I had, I put the query for future readers

CriteriaBuilder cb = sesion.getCriteriaBuilder();
CriteriaQuery<Materia> cq = cb.createQuery(Materia.class);
Root<Materia> root = cq.from(Materia.class);
cq.select(root);
cq.where(root.get("grado").isNull());
Query query = sesion.createQuery(cq);
List<Materia> results = query.getResultList();

Solution

  • Try the following:

    To Grado model add

    @OneToMany(orphanRemoval = true)
    @JoinColumn(name="grado_id")
    private List<Materia> materias;
    

    And To Materia Model add

    @ManyToOne
    private Grado grado ;
    

    Adding the above to the Materia model will prevent a join table from being created.