Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

CriteriaBuilder Predicate isMember using only entity ID

Tags:

hibernate

jpa

Given the following entities, how can I construct a JPA Predicate to select only those Items that have a Category with a given ID in their categories set?

@Entity
public class Item
{
  @Id
  private String id;

  private String name;

  @JoinTable(name="category_items",
    joinColumns={@JoinColumn(name="item_id")},
    inverseJoinColumns={@JoinColumn(name="category_id")})
  private Set<Category> categories;

  /* etc */
}

@Entity
public class Category
{
  @Id
  private String id;

  private String name;

  /* etc */
}

I think I can do it if I have the Category object to hand:

Predicate buildPredicate( CriteriaBuilder cb, Root root, Category category )
{
  Expression<Collection<Category>> categories = root.get( "categories" );
  return cb.isMember( category, categories );
}

But my question is : Can I do it using only the Category.id string? In SQL it would be something like

SELECT item.id, item.name FROM item JOIN category_items ON item.id = category_items.item_id WHERE category_items.category_id=?

which doesn't go near the category table.

I ask because I want to avoid having to create or retrieve a new Category instance when all I need is its ID, which I already have.

Thanks for any help!

like image 740
Alex Avatar asked Oct 21 '22 09:10

Alex


1 Answers

I eventually solved this using join and not isMember:

EntityManager em = getEntityManager();
CriteriaBuilder cb = em.getCriteriaBuilder();
CriteriaQuery<Item> cq = cb.createQuery( Item.class );
Root from = cq.from( Item.class );
From join = from.join( "categories" );
Path<Item> p = join.get( "id" );
Predicate predicate = cb.equal( p, "my_category_id" );
cq.where( predicate );
cq.select( from );
TypedQuery<Item> typedQuery = em.createQuery( cq );
List<Item> resultList = typedQuery.getResultList();
like image 158
Alex Avatar answered Oct 24 '22 04:10

Alex