JPA & Criteria API - Select only specific columns
One of the JPA ways for getting only particular columns is to ask for a Tuple object.
In your case you would need to write something like this:
CriteriaQuery<Tuple> cq = builder.createTupleQuery();
// write the Root, Path elements as usual
Root<EntityClazz> root = cq.from(EntityClazz.class);
cq.multiselect(root.get(EntityClazz_.ID), root.get(EntityClazz_.VERSION)); //using metamodel
List<Tuple> tupleResult = em.createQuery(cq).getResultList();
for (Tuple t : tupleResult) {
Long id = (Long) t.get(0);
Long version = (Long) t.get(1);
}
Another approach is possible if you have a class representing the result, like T
in your case. T
doesn't need to be an Entity class. If T
has a constructor like:
public T(Long id, Long version)
then you can use T
directly in your CriteriaQuery
constructor:
CriteriaQuery<T> cq = builder.createQuery(T.class);
// write the Root, Path elements as usual
Root<EntityClazz> root = cq.from(EntityClazz.class);
cq.multiselect(root.get(EntityClazz_.ID), root.get(EntityClazz_.VERSION)); //using metamodel
List<T> result = em.createQuery(cq).getResultList();
See this link for further reference.
cq.select(cb.construct(entityClazz.class, root.get("ID"), root.get("VERSION"))); // HERE IS NO ERROR
https://wiki.eclipse.org/EclipseLink/UserGuide/JPA/Basic_JPA_Development/Querying/Criteria#Constructors
First of all, I don't really see why you would want an object having only ID and Version, and all other props to be nulls. However, here is some code which will do that for you (which doesn't use JPA Em, but normal Hibernate. I assume you can find the equivalence in JPA or simply obtain the Hibernate Session obj from the em delegate Accessing Hibernate Session from EJB using EntityManager ):
List<T> results = session.createCriteria(entityClazz)
.setProjection( Projections.projectionList()
.add( Property.forName("ID") )
.add( Property.forName("VERSION") )
)
.setResultTransformer(Transformers.aliasToBean(entityClazz);
.list();
This will return a list of Objects having their ID and Version set and all other props to null, as the aliasToBean transformer won't be able to find them. Again, I am uncertain I can think of a situation where I would want to do that.