Boa noite, fiz uma implementação diferente, e também gostaria de compartilhar, e tabém ouvir possiveis criticas e melhorias.
Pagina
<h:form>
<p:dataTable value="#{index.data}" var="item" rows="10">
<p:column headerText="Nome" sortBy="#{item.name}" filterBy="#{item.name}">
<h:outputText value="#{item.name}"/>
</p:column>
<p:column headerText="Addressline1" sortBy="#{item.addressline1}" filterBy="#{item.addressline1}">
<h:outputText value="#{item.addressline1}"/>
</p:column>
<p:column headerText="Addressline2" sortBy="#{item.addressline2}" filterBy="#{item.addressline2}">
<h:outputText value="#{item.addressline2}"/>
</p:column>
</p:dataTable>
</h:form>
ManagedBean
package com.lazilist.mb;
import com.lazilist.commons.LazyList;
import com.lazilist.entity.Customer;
import com.lazilist.repo.CustomerFacade;
import javax.faces.bean.ManagedBean;
import javax.faces.bean.ViewScoped;
import javax.inject.Inject;
@ManagedBean
@ViewScoped
public class Index {
@Inject
private CustomerFacade customerFacade;//Aqui é uma implementação do AbstractFacade<T>
private LazyList<Customer> data;
private Customer customer;
public Customer getCustomer() {
return customer;
}
public void setCustomer(Customer customer) {
this.customer = customer;
}
public LazyList<Customer> getData() {
if (data == null) {
data = new LazyList(customerFacade);
}
return data;
}
public void setData(LazyList<Customer> data) {
this.data = data;
}
}
LazyList, aqui está a implementação
package com.lazilist.commons;
import com.lazilist.repo.AbstractFacade;
import java.util.List;
import java.util.Map;
import org.primefaces.model.LazyDataModel;
import org.primefaces.model.SortOrder;
public class LazyList<T> extends LazyDataModel<Beanable> {
private AbstractFacade<Beanable> facade;
public LazyList(AbstractFacade<Beanable> facade) {
this.facade = facade;
}
private static final long serialVersionUID = 1L;
protected List<Beanable> data;
@Override
public List<Beanable> load(int startingAt, int maxPerPage, String sortField, SortOrder sortOrder, Map<String, String> filters) {
data = facade.getByRangeSortFilter(startingAt, maxPerPage, sortField, sortOrder, filters);
setRowCount(facade.countFilter(filters));
setPageSize(maxPerPage);
return data;
}
@Override
public Object getRowKey(Beanable bean) {
return bean.getId();
}
@Override
public Beanable getRowData(String beanId) {
if (beanId != null && !beanId.equals("") && !beanId.equals("null")) {
Object id = Integer.valueOf(beanId);
for (Beanable bean : data) {
if (id.equals(bean.getId())) {
return bean;
}
}
}
return null;
}
}
Beanable
/*
* To change this template, choose Tools | Templates
* and open the template in the editor.
*/
package com.lazilist.commons;
/**
*
* @author flavio
*/
public interface Beanable {
public Object getId();
}
Metodos nescessarios no AbstractFacade
public List<T> getByRangeSortFilter(int startingAt, int maxPerPage, String sortField, SortOrder sortOrder, Map<String, String> filters) {
CriteriaBuilder cb = getEntityManager().getCriteriaBuilder();
CriteriaQuery<T> q = cb.createQuery(entityClass);
Root<T> c = q.from(entityClass);
q.select(c);
if (filters != null && !filters.isEmpty()) {
Predicate[] predicates = new Predicate[filters.size()];
int i = 0;
for (Map.Entry<String, String> entry : filters.entrySet()) {
String key = entry.getKey();
String val = entry.getValue();
Expression<String> path = c.get(key);
try {
if (entityClass.getDeclaredField(key).getType().equals(String.class)) {
predicates[i] = cb.and(cb.like(path, "%" + val + "%"));
} else {
predicates[i] = cb.and(cb.equal(path, val));
}
} catch (NoSuchFieldException ex) {
Logger.getLogger(AbstractFacade.class.getName()).log(Level.SEVERE, null, ex + " entityClass:" + entityClass.toString());
} catch (SecurityException ex) {
Logger.getLogger(AbstractFacade.class.getName()).log(Level.SEVERE, null, ex + " entityClass:" + entityClass.toString());
}
i++;
}
q.where(predicates);
}
if (sortField != null && !sortField.isEmpty()) {
if (sortOrder.equals(SortOrder.ASCENDING)) {
q.orderBy(cb.asc(c.get(sortField)));
} else if (sortOrder.equals(SortOrder.DESCENDING)) {
q.orderBy(cb.desc(c.get(sortField)));
}
}
TypedQuery<T> query = getEntityManager().createQuery(q);
query.setMaxResults(maxPerPage);
query.setFirstResult(startingAt);
return query.getResultList();
}
public int countFilter(Map<String, String> filters) {
CriteriaBuilder cb = getEntityManager().getCriteriaBuilder();
CriteriaQuery q = cb.createQuery(entityClass);
Root<T> c = q.from(entityClass);
q.select(cb.count(c));
if (filters != null && !filters.isEmpty()) {
Predicate[] predicates = new Predicate[filters.size()];
int i = 0;
for (Map.Entry<String, String> entry : filters.entrySet()) {
String key = entry.getKey();
String val = entry.getValue();
Expression<String> path = c.get(key);
try {
if (entityClass.getDeclaredField(key).getType().equals(String.class)) {
predicates[i] = cb.and(cb.like(path, "%" + val + "%"));
} else {
predicates[i] = cb.and(cb.equal(path, val));
}
} catch (NoSuchFieldException ex) {
Logger.getLogger(AbstractFacade.class.getName()).log(Level.SEVERE, null, ex + " entityClass:" + entityClass.toString());
} catch (SecurityException ex) {
Logger.getLogger(AbstractFacade.class.getName()).log(Level.SEVERE, null, ex + " entityClass:" + entityClass.toString());
}
i++;
}
q.where(predicates);
}
TypedQuery<T> query = getEntityManager().createQuery(q);
return ((Long) query.getSingleResult()).intValue();
}
Como eu disse podem criticar, mas espero que que seja útil para alguem.