primefaces: DataTable: Sort is lost after data refresh

Describe the defect When using a DataTable with sortable columns, the sort order is lost after refreshing/replacing the underlying data model (List) in an AJAX request. The header still indicates the sorting in the column, but the data is no longer ordnered. In PF 8.0 this still worked, but since 10.0 the sorting is no longer kept after the list is recreated.

Sometimes it is necessary to e.g. periodically update the displayed data from DB, but still keep the currently selected sorting.

Environment:

  • PF Version: 10.0.7 (also tested the current master 11.0.0-SNAPSHOT with commit 9ea38543)
  • JSF + version: Mojarra 2.3.9
  • Affected browsers: Firefox

To Reproduce Steps to reproduce the behavior:

  1. Display Datatable in a view
  2. Sort by clicking a sortable header.
  3. The data is correctly sorted by this column. THe column header indicates sorting.
  4. Trigger reloading the data for this datatable by AJAX (and alos the update of the datatable), e.g. via a CommandButton
  5. Now the table header still indicates that the data is sorted by this column. But the updated data is no longer sorted

Expected behavior Even after a reloading of the data, I would expect the data in the table to be sorted by the column. This was also the behaviour in PrimeFaces 8.0.

Example XHTML

<h:form>
    <p:dataTable value="#{dataBean.data}" var="data">
        <p:column headerText="Text" sortBy="#{data.text}">
            <h:outputText value="#{data.text}"/>
        </p:column>
        <p:column headerText="Number" sortBy="#{data.num}">
            <h:outputText value="#{data.num}"/>
        </p:column>
    </p:dataTable>
    <h:panelGroup>
        <p:commandButton value="Refresh" process="@this" update="@form" actionListener="#{dataBean.refresh}" />
    </h:panelGroup>
</h:form>

Example Bean

@ViewScoped
@Named("dataBean")
public class DataBean implements Serializable {

    public static class Data {

        private final String text;

        private final int num;

        public Data(String text, int num) {
            this.text = text;
            this.num = num;
        }

        public String getText() {
            return text;
        }

        public int getNum() {
            return num;
        }
    }

    private List<Data> data;

    public List<Data> getData() {
        return data;
    }

    @PostConstruct
    public void refresh() {
        List<Data> newData = new ArrayList<>();
        for (int i = 0; i < 10; i++) {
            // Generate random letter and number to test sorting
            newData.add(new Data("Data " + ((char) ((int) 'A' + ThreadLocalRandom.current().nextInt(26))),
                    ThreadLocalRandom.current().nextInt(100)));
        }
        this.data = newData;
    }

}

About this issue

  • Original URL
  • State: closed
  • Created 3 years ago
  • Comments: 25 (19 by maintainers)

Commits related to this issue

Most upvoted comments

Fixed it. Though, no idea why setRowIndex is called while it’s not for filtering.