SerializableDataModel, server-side pagination, sorting and filtering: problem with event
aligi Aug 10, 2010 4:22 AMI have implemented my own SerializableDataModel for server-side pagination, sorting and filtering. Everything is shown correctly but if I use a boolean checkbox the values are not transfered to the manager. For testing purpose I have added a a4j:support tag which calls a method of the manager, but this method is never reached. In the debug mode some methods of the serializabledatamodel are called but how i said it never comes to the manager. If I use a normal list instead of the SerializableDataModel everything works fine.
seam version: 2.2.0.GA, richfaces: 3.3.3.Final
.xhtml
<rich:dataTable value="#{einladungUstManager.personsForEinladungPaginatingDataModel}" var="personvar" rowKeyVar="rowIndex" rows="5" reRender="ds2" id="simpletable" width="100%" rowClasses="firstrow,secondrow"> <f:facet name="header"> <h:outputText value="Persons" /> </f:facet> <rich:column width="10%"> <h:selectBooleanCheckbox value="#{einladungUstManager.selectedPersonVsnrMapForEinladung[personvar.vsnr]}"> <a4j:support event="onchange" action="#{einladungUstManager.changeSelectEvent}" bypassUpdates="false" /> </h:selectBooleanCheckbox> </rich:column> </rich:dataTable> <rich:datascroller id="ds2" renderIfSinglePage="false" for="simpletable"></rich:datascroller>
SerializableDataModel
public abstract class PaginatingDataModel<T, U> extends SerializableDataModel implements Modifiable { private static final long serialVersionUID = 2954923950179861809L; protected U currentPk; protected int rowIndex; protected boolean descending = true; protected String sortField = null; protected List<SearchCriterion> filterCriteriaList = new ArrayList<SearchCriterion>(); protected boolean detached = false; protected List<U> wrappedKeys = new ArrayList<U>(); protected Integer rowCount; protected Map<U, T> wrappedData = new HashMap<U, T>(); /** * * @see org.ajax4jsf.model.ExtendedDataModel#getRowKey() */ @Override public Object getRowKey() { return currentPk; } /** * * @see org.ajax4jsf.model.ExtendedDataModel#setRowKey(java.lang.Object) */ @SuppressWarnings("unchecked") @Override public void setRowKey(final Object key) { this.currentPk = (U) key; } /** * * @see org.ajax4jsf.model.SerializableDataModel#update() */ @Override public void update() { detached = false; } /** * * @see org.ajax4jsf.model.ExtendedDataModel#getSerializableModel(org.ajax4jsf.model.Range) */ @Override public SerializableDataModel getSerializableModel(final Range range) { if (wrappedKeys != null) { detached = true; return this; } return null; } /** * * @see javax.faces.model.DataModel#setRowIndex(int) */ @Override public void setRowIndex(final int arg0) { rowIndex = arg0; } /** * * @see javax.faces.model.DataModel#setWrappedData(java.lang.Object) */ @Override public void setWrappedData(final Object data) { throw new UnsupportedOperationException(); } /** * * @see javax.faces.model.DataModel#getRowIndex() */ @Override public int getRowIndex() { return rowIndex; } /** * * @see javax.faces.model.DataModel#getWrappedData() */ @Override public Object getWrappedData() { throw new UnsupportedOperationException(); } /** * * @see org.ajax4jsf.model.ExtendedDataModel#walk(javax.faces.context.FacesContext, org.ajax4jsf.model.DataVisitor, org.ajax4jsf.model.Range, * java.lang.Object) */ @Override public void walk(final FacesContext context, final DataVisitor visitor, final Range range, final Object argument) throws IOException { try { final int firstRow = ((SequenceRange) range).getFirstRow(); final int numberOfRows = ((SequenceRange) range).getRows(); int rowIndex = firstRow; if (detached) { for (final U key : wrappedKeys) { setRowKey(key); setRowIndex(rowIndex++); visitor.process(context, key, argument); } } else { // if not serialized, than we request data from data provider wrappedKeys = new ArrayList<U>(); for (final T object : findObjects(firstRow, numberOfRows, sortField, filterCriteriaList, descending)) { setRowIndex(rowIndex++); wrappedKeys.add(getId(object)); wrappedData.put(getId(object), object); visitor.process(context, getId(object), argument); } } } catch (Exception e) { throw new IOException(); } } /** * * @see javax.faces.model.DataModel#isRowAvailable() */ @Override public boolean isRowAvailable() { if (currentPk == null) { return false; } if (wrappedKeys.contains(currentPk)) { return true; } if (wrappedData.entrySet().contains(currentPk)) { return true; } try { if (getObjectById(currentPk) != null) { return true; } } catch (final Exception e) { } return false; } /** * * @see javax.faces.model.DataModel#getRowData() */ @Override public Object getRowData() throws FacesException, IllegalArgumentException { try { if (currentPk == null) { return null; } T object = wrappedData.get(currentPk); if (object == null) { object = getObjectById(currentPk); wrappedData.put(currentPk, object); } return object; } catch (FacesException e) { throw e; } catch (IllegalArgumentException e) { throw e; } catch (Exception e) { throw new FacesException(); } } /** * * @see javax.faces.model.DataModel#getRowCount() */ @Override public int getRowCount() throws FacesException { try { if (rowCount == null) { rowCount = getNumRecords(filterCriteriaList).intValue(); } return rowCount; } catch (Exception e) { throw new FacesException(); } } @Override public void modify(List<FilterField> filterFields, List<SortField2> sortFields) { filterCriteriaList.clear(); SortField2 sortField2 = null; String expressionStr = null; ExtendedFilterField extendedFilterField = null; Expression expression = null; String value = null; if (sortFields != null && !sortFields.isEmpty()) { sortField2 = sortFields.get(0); expression = sortField2.getExpression(); expressionStr = expression.getExpressionString(); if (!expression.isLiteralText()) { expressionStr = expressionStr.replaceAll("[#|$]{1}\\{.*?\\.", "").replaceAll("\\}", ""); } this.sortField = expressionStr; if (sortField2.getOrdering() == Ordering.DESCENDING) { this.descending = true; } else { this.descending = false; } } if (filterFields != null && !filterFields.isEmpty()) { for (FilterField filterField : filterFields) { if (filterField instanceof ExtendedFilterField) { extendedFilterField = (ExtendedFilterField) filterField; value = extendedFilterField.getFilterValue(); if (value != null && !value.equals("")) { expression = extendedFilterField.getExpression(); expressionStr = expression.getExpressionString(); if (!expression.isLiteralText()) { expressionStr = expressionStr.replaceAll("[#|$]{1}\\{.*?\\.", "").replaceAll("\\}", ""); } filterCriteriaList.add(new SearchCriterion(expressionStr, value, CriterionOperator.LIKE, true)); } } } } } /** * @param object * * @return U */ public abstract U getId(T object) throws Exception; /** * * @param firstRow * * @param numberOfRows * * @param sortField * * @param descending * * @return List<T> */ public abstract List<T> findObjects(int firstRow, int numberOfRows, String sortField, List<SearchCriterion> filterCriteriaList, boolean descending) throws Exception; /** * * @param id * * @return T */ public abstract T getObjectById(U id) throws Exception; /** * * @return Long */ public abstract Long getNumRecords(List<SearchCriterion> filterCriteriaList) throws Exception; public abstract void destroy(); }
PersonsForEinladungPaginatingDataModel
@Name("personsForEinladungPaginatingDataModel") public class PersonsForEinladungPaginatingDataModel extends PaginatingDataModel<Person, Long> { private static final long serialVersionUID = 1868068053701471139L; @Logger private Log log; @In private EinladungUstService einladungUstService; @In private PersonService personService; @In(required = false) public Suchvorlage suchvorlage = new Suchvorlage(); @In(required = false, value = "untersuchungsstelle_einladung") private Untersuchungsstelle untersuchungsstelle = new Untersuchungsstelle(); @In(required = false, value = "untersuchungstag_einladung") private Date untersuchungstag = new Date(); /** * @see PaginatingDataModel#getId */ @Override public Long getId(Person person) throws Exception { try { return person.getId(); } catch (Exception e) { throw e; } } /** * @see PaginatingDataModel#findObjects */ @Override public List<Person> findObjects(int firstRow, int maxResult, String sortField, List<SearchCriterion> filterCriteriaList, boolean descending) throws Exception { try { return einladungUstService.getPersonsForEinladungRange(firstRow, maxResult, sortField, filterCriteriaList, descending, suchvorlage, untersuchungsstelle, untersuchungstag); } catch (Exception e) { log.warn("findObjects(int,int,String,List<SearchCriterion>,boolean) - Exception: #0", e.getMessage()); throw e; } } /** * @see PaginatingDataModel#getObjectById(java.lang.Object) */ @Override public Person getObjectById(Long id) throws Exception { try { return personService.getPersonById(id); } catch (Exception e) { throw e; } } /** * * @see PaginatingDataModel#getNumRecords */ @Override public Long getNumRecords(List<SearchCriterion> filterCriteriaList) throws Exception { try { return einladungUstService.getCountPersonsForEinladungRange(filterCriteriaList, suchvorlage, untersuchungsstelle, untersuchungstag); } catch (Exception e) { throw e; } } /** * Delete the bean. */ @Override @Destroy @Remove public void destroy() { wrappedData.clear(); wrappedKeys.clear(); } }
Manager
@Name("einladungUstManager") @Scope(ScopeType.SESSION) public class EinladungUstManager { private Map<String, Boolean> selectedPersonVsnrMapForEinladung; @In(create = true) private PersonsForEinladungPaginatingDataModel personsForEinladungPaginatingDataModel; public EinladungUstManager() { selectedPersonVsnrMapForEinladung = new HashMap<String, Boolean>(); } public Map<String, Boolean> getSelectedPersonVsnrMapForEinladung() { return selectedPersonVsnrMapForEinladung; } public void setSelectedPersonVsnrMapForEinladung(Map<String, Boolean> selectedPersonVsnrMapForEinladung) { this.selectedPersonVsnrMapForEinladung = selectedPersonVsnrMapForEinladung; } public PersonsForEinladungPaginatingDataModel getPersonsForEinladungPaginatingDataModel() { return personsForEinladungPaginatingDataModel; } public void setPersonsForEinladungPaginatingDataModel(PersonsForEinladungPaginatingDataModel personsForEinladungPaginatingDataModel) { this.personsForEinladungPaginatingDataModel = personsForEinladungPaginatingDataModel; } public void changeSelectEvent() throws Exception { try { System.out.print("test"); } catch (Exception e) { throw e; } } }