Java.lang.UnsupportedOperationException: getRowData (String rowKey) should be implemented when the underlying rowKey algorithm is not used

I upgraded PrimeFaces from final 5.1 to final 5.2 (community release). I have a <p:dataTable> that lazily loads like this (minimal example to reproduce the problem for pure testing purpose only).

 <p:dataTable var="row" value="#{testManagedBean}" lazy="true" editable="true" rowKey="#{row.fruitId}" selection="#{testManagedBean.selectedValues}" rows="50"> <p:column selectionMode="multiple"/> <p:ajax event="rowEdit" listener="#{testManagedBean.onRowEdit}"/> <p:column headerText="Id"> <h:outputText value="#{row.fruitId}"/> </p:column> <p:column headerText="Fruit Name"> <p:cellEditor> <f:facet name="output"> <h:outputText value="#{row.fruitName}"/> </f:facet> <f:facet name="input"> <p:inputText value="#{row.fruitName}"/> </f:facet> </p:cellEditor> </p:column> <p:column headerText="Price"> <p:cellEditor> <f:facet name="output"> <h:outputText value="#{row.price}"/> </f:facet> <f:facet name="input"> <p:inputText value="#{row.price}"/> </f:facet> </p:cellEditor> </p:column> <p:column headerText="Edit"> <p:rowEditor/> </p:column> </p:dataTable> 

Corresponding managed bean:

 @Named @ViewScoped public class TestManagedBean extends LazyDataModel<Fruit> implements Serializable { private List<Fruit> selectedValues; // Getter & setter. private static final long serialVersionUID = 1L; public TestManagedBean() {} private List<Fruit> init() { List<Fruit> fruits = new ArrayList<Fruit>(); Fruit fruit = new Fruit(); fruit.setFruitId(1); fruit.setFruitName("Mango"); fruit.setPrice(500D); fruits.add(fruit); fruit = new Fruit(); fruit.setFruitId(2); fruit.setFruitName("Guava"); fruit.setPrice(300D); fruits.add(fruit); fruit = new Fruit(); fruit.setFruitId(3); fruit.setFruitName("Apple"); fruit.setPrice(600D); fruits.add(fruit); return fruits; } @Override public List<Fruit> load(int first, int pageSize, String sortField, SortOrder sortOrder, Map<String, Object> filters) { List<Fruit> fruits = init(); setRowCount(fruits.size()); return fruits; } public void onRowEdit(RowEditEvent event) { System.out.println("id : "+((Fruit)event.getObject()).getFruitId()); } } 

When editing the onRowEdit() method, it is assumed that it is bound,

 <p:ajax event="rowEdit" listener="#{testManagedBean.onRowEdit}"/> 

When the line is in edit mode and the update button is pressed, ticked, it raises the following exception.

 Info: java.lang.UnsupportedOperationException: getRowData(String rowKey) must be implemented when basic rowKey algorithm is not used. java.lang.UnsupportedOperationException: getRowData(String rowKey) must be implemented when basic rowKey algorithm is not used. at org.primefaces.model.LazyDataModel.getRowData(LazyDataModel.java:95) at org.primefaces.component.datatable.DataTable.getRowData(DataTable.java:1214) at org.primefaces.component.datatable.feature.SelectionFeature.decodeMultipleSelection(SelectionFeature.java:90) at org.primefaces.component.datatable.feature.SelectionFeature.decode(SelectionFeature.java:48) at org.primefaces.component.datatable.DataTableRenderer.decode(DataTableRenderer.java:62) at javax.faces.component.UIComponentBase.decode(UIComponentBase.java:834) at org.primefaces.component.api.UIData.processDecodes(UIData.java:281) at com.sun.faces.context.PartialViewContextImpl$PhaseAwareVisitCallback.visit(PartialViewContextImpl.java:573) at com.sun.faces.component.visit.PartialVisitContext.invokeVisitCallback(PartialVisitContext.java:183) at org.primefaces.component.api.UIData.visitTree(UIData.java:821) at javax.faces.component.UIComponent.visitTree(UIComponent.java:1690) at javax.faces.component.UIForm.visitTree(UIForm.java:380) at javax.faces.component.UIComponent.visitTree(UIComponent.java:1690) at javax.faces.component.UIComponent.visitTree(UIComponent.java:1690) at com.sun.faces.context.PartialViewContextImpl.processComponents(PartialViewContextImpl.java:403) at com.sun.faces.context.PartialViewContextImpl.processPartial(PartialViewContextImpl.java:266) at org.primefaces.context.PrimePartialViewContext.processPartial(PrimePartialViewContext.java:60) at javax.faces.component.UIViewRoot.processDecodes(UIViewRoot.java:930) at com.sun.faces.lifecycle.ApplyRequestValuesPhase.execute(ApplyRequestValuesPhase.java:78) at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:101) at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:198) at javax.faces.webapp.FacesServlet.service(FacesServlet.java:660) at org.apache.catalina.core.StandardWrapper.service(StandardWrapper.java:1682) at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:318) at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:160) at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:734) at org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:673) at com.sun.enterprise.web.WebPipeline.invoke(WebPipeline.java:99) at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:174) at org.apache.catalina.connector.CoyoteAdapter.doService(CoyoteAdapter.java:415) at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:282) at com.sun.enterprise.v3.services.impl.ContainerMapper$HttpHandlerCallable.call(ContainerMapper.java:459) at com.sun.enterprise.v3.services.impl.ContainerMapper.service(ContainerMapper.java:167) at org.glassfish.grizzly.http.server.HttpHandler.runService(HttpHandler.java:201) at org.glassfish.grizzly.http.server.HttpHandler.doHandle(HttpHandler.java:175) at org.glassfish.grizzly.http.server.HttpServerFilter.handleRead(HttpServerFilter.java:235) at org.glassfish.grizzly.filterchain.ExecutorResolver$9.execute(ExecutorResolver.java:119) at org.glassfish.grizzly.filterchain.DefaultFilterChain.executeFilter(DefaultFilterChain.java:284) at org.glassfish.grizzly.filterchain.DefaultFilterChain.executeChainPart(DefaultFilterChain.java:201) at org.glassfish.grizzly.filterchain.DefaultFilterChain.execute(DefaultFilterChain.java:133) at org.glassfish.grizzly.filterchain.DefaultFilterChain.process(DefaultFilterChain.java:112) at org.glassfish.grizzly.ProcessorExecutor.execute(ProcessorExecutor.java:77) at org.glassfish.grizzly.nio.transport.TCPNIOTransport.fireIOEvent(TCPNIOTransport.java:561) at org.glassfish.grizzly.strategies.AbstractIOStrategy.fireIOEvent(AbstractIOStrategy.java:112) at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy.run0(WorkerThreadIOStrategy.java:117) at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy.access$100(WorkerThreadIOStrategy.java:56) at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy$WorkerThreadRunnable.run(WorkerThreadIOStrategy.java:137) at org.glassfish.grizzly.threadpool.AbstractThreadPool$Worker.doWork(AbstractThreadPool.java:565) at org.glassfish.grizzly.threadpool.AbstractThreadPool$Worker.run(AbstractThreadPool.java:545) at java.lang.Thread.run(Thread.java:745) Warning: java.lang.UnsupportedOperationException: getRowData(String rowKey) must be implemented when basic rowKey algorithm is not used. javax.faces.FacesException: java.lang.UnsupportedOperationException: getRowData(String rowKey) must be implemented when basic rowKey algorithm is not used. at com.sun.faces.context.PartialViewContextImpl.processPartial(PartialViewContextImpl.java:273) at org.primefaces.context.PrimePartialViewContext.processPartial(PrimePartialViewContext.java:60) at javax.faces.component.UIViewRoot.processDecodes(UIViewRoot.java:930) at com.sun.faces.lifecycle.ApplyRequestValuesPhase.execute(ApplyRequestValuesPhase.java:78) at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:101) at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:198) at javax.faces.webapp.FacesServlet.service(FacesServlet.java:660) at org.apache.catalina.core.StandardWrapper.service(StandardWrapper.java:1682) at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:318) at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:160) at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:734) at org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:673) at com.sun.enterprise.web.WebPipeline.invoke(WebPipeline.java:99) at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:174) at org.apache.catalina.connector.CoyoteAdapter.doService(CoyoteAdapter.java:415) at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:282) at com.sun.enterprise.v3.services.impl.ContainerMapper$HttpHandlerCallable.call(ContainerMapper.java:459) at com.sun.enterprise.v3.services.impl.ContainerMapper.service(ContainerMapper.java:167) at org.glassfish.grizzly.http.server.HttpHandler.runService(HttpHandler.java:201) at org.glassfish.grizzly.http.server.HttpHandler.doHandle(HttpHandler.java:175) at org.glassfish.grizzly.http.server.HttpServerFilter.handleRead(HttpServerFilter.java:235) at org.glassfish.grizzly.filterchain.ExecutorResolver$9.execute(ExecutorResolver.java:119) at org.glassfish.grizzly.filterchain.DefaultFilterChain.executeFilter(DefaultFilterChain.java:284) at org.glassfish.grizzly.filterchain.DefaultFilterChain.executeChainPart(DefaultFilterChain.java:201) at org.glassfish.grizzly.filterchain.DefaultFilterChain.execute(DefaultFilterChain.java:133) at org.glassfish.grizzly.filterchain.DefaultFilterChain.process(DefaultFilterChain.java:112) at org.glassfish.grizzly.ProcessorExecutor.execute(ProcessorExecutor.java:77) at org.glassfish.grizzly.nio.transport.TCPNIOTransport.fireIOEvent(TCPNIOTransport.java:561) at org.glassfish.grizzly.strategies.AbstractIOStrategy.fireIOEvent(AbstractIOStrategy.java:112) at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy.run0(WorkerThreadIOStrategy.java:117) at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy.access$100(WorkerThreadIOStrategy.java:56) at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy$WorkerThreadRunnable.run(WorkerThreadIOStrategy.java:137) at org.glassfish.grizzly.threadpool.AbstractThreadPool$Worker.doWork(AbstractThreadPool.java:565) at org.glassfish.grizzly.threadpool.AbstractThreadPool$Worker.run(AbstractThreadPool.java:545) at java.lang.Thread.run(Thread.java:745) Caused by: java.lang.UnsupportedOperationException: getRowData(String rowKey) must be implemented when basic rowKey algorithm is not used. at org.primefaces.model.LazyDataModel.getRowData(LazyDataModel.java:95) at org.primefaces.component.datatable.DataTable.getRowData(DataTable.java:1214) at org.primefaces.component.datatable.feature.SelectionFeature.decodeMultipleSelection(SelectionFeature.java:90) at org.primefaces.component.datatable.feature.SelectionFeature.decode(SelectionFeature.java:48) at org.primefaces.component.datatable.DataTableRenderer.decode(DataTableRenderer.java:62) at javax.faces.component.UIComponentBase.decode(UIComponentBase.java:834) at org.primefaces.component.api.UIData.processDecodes(UIData.java:281) at com.sun.faces.context.PartialViewContextImpl$PhaseAwareVisitCallback.visit(PartialViewContextImpl.java:573) at com.sun.faces.component.visit.PartialVisitContext.invokeVisitCallback(PartialVisitContext.java:183) at org.primefaces.component.api.UIData.visitTree(UIData.java:821) at javax.faces.component.UIComponent.visitTree(UIComponent.java:1690) at javax.faces.component.UIForm.visitTree(UIForm.java:380) at javax.faces.component.UIComponent.visitTree(UIComponent.java:1690) at javax.faces.component.UIComponent.visitTree(UIComponent.java:1690) at com.sun.faces.context.PartialViewContextImpl.processComponents(PartialViewContextImpl.java:403) at com.sun.faces.context.PartialViewContextImpl.processPartial(PartialViewContextImpl.java:266) ... 34 more Severe: java.lang.UnsupportedOperationException: getRowData(String rowKey) must be implemented when basic rowKey algorithm is not used. at org.primefaces.model.LazyDataModel.getRowData(LazyDataModel.java:95) at org.primefaces.component.datatable.DataTable.getRowData(DataTable.java:1214) at org.primefaces.component.datatable.feature.SelectionFeature.decodeMultipleSelection(SelectionFeature.java:90) at org.primefaces.component.datatable.feature.SelectionFeature.decode(SelectionFeature.java:48) at org.primefaces.component.datatable.DataTableRenderer.decode(DataTableRenderer.java:62) at javax.faces.component.UIComponentBase.decode(UIComponentBase.java:834) at org.primefaces.component.api.UIData.processDecodes(UIData.java:281) at com.sun.faces.context.PartialViewContextImpl$PhaseAwareVisitCallback.visit(PartialViewContextImpl.java:573) at com.sun.faces.component.visit.PartialVisitContext.invokeVisitCallback(PartialVisitContext.java:183) at org.primefaces.component.api.UIData.visitTree(UIData.java:821) at javax.faces.component.UIComponent.visitTree(UIComponent.java:1690) at javax.faces.component.UIForm.visitTree(UIForm.java:380) at javax.faces.component.UIComponent.visitTree(UIComponent.java:1690) at javax.faces.component.UIComponent.visitTree(UIComponent.java:1690) at com.sun.faces.context.PartialViewContextImpl.processComponents(PartialViewContextImpl.java:403) at com.sun.faces.context.PartialViewContextImpl.processPartial(PartialViewContextImpl.java:266) at org.primefaces.context.PrimePartialViewContext.processPartial(PrimePartialViewContext.java:60) at javax.faces.component.UIViewRoot.processDecodes(UIViewRoot.java:930) at com.sun.faces.lifecycle.ApplyRequestValuesPhase.execute(ApplyRequestValuesPhase.java:78) at com.sun.faces.lifecycle.Phase.doPhase(Phase.java:101) at com.sun.faces.lifecycle.LifecycleImpl.execute(LifecycleImpl.java:198) at javax.faces.webapp.FacesServlet.service(FacesServlet.java:660) at org.apache.catalina.core.StandardWrapper.service(StandardWrapper.java:1682) at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:318) at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:160) at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:734) at org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:673) at com.sun.enterprise.web.WebPipeline.invoke(WebPipeline.java:99) at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:174) at org.apache.catalina.connector.CoyoteAdapter.doService(CoyoteAdapter.java:415) at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:282) at com.sun.enterprise.v3.services.impl.ContainerMapper$HttpHandlerCallable.call(ContainerMapper.java:459) at com.sun.enterprise.v3.services.impl.ContainerMapper.service(ContainerMapper.java:167) at org.glassfish.grizzly.http.server.HttpHandler.runService(HttpHandler.java:201) at org.glassfish.grizzly.http.server.HttpHandler.doHandle(HttpHandler.java:175) at org.glassfish.grizzly.http.server.HttpServerFilter.handleRead(HttpServerFilter.java:235) at org.glassfish.grizzly.filterchain.ExecutorResolver$9.execute(ExecutorResolver.java:119) at org.glassfish.grizzly.filterchain.DefaultFilterChain.executeFilter(DefaultFilterChain.java:284) at org.glassfish.grizzly.filterchain.DefaultFilterChain.executeChainPart(DefaultFilterChain.java:201) at org.glassfish.grizzly.filterchain.DefaultFilterChain.execute(DefaultFilterChain.java:133) at org.glassfish.grizzly.filterchain.DefaultFilterChain.process(DefaultFilterChain.java:112) at org.glassfish.grizzly.ProcessorExecutor.execute(ProcessorExecutor.java:77) at org.glassfish.grizzly.nio.transport.TCPNIOTransport.fireIOEvent(TCPNIOTransport.java:561) at org.glassfish.grizzly.strategies.AbstractIOStrategy.fireIOEvent(AbstractIOStrategy.java:112) at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy.run0(WorkerThreadIOStrategy.java:117) at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy.access$100(WorkerThreadIOStrategy.java:56) at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy$WorkerThreadRunnable.run(WorkerThreadIOStrategy.java:137) at org.glassfish.grizzly.threadpool.AbstractThreadPool$Worker.doWork(AbstractThreadPool.java:565) at org.glassfish.grizzly.threadpool.AbstractThreadPool$Worker.run(AbstractThreadPool.java:545) at java.lang.Thread.run(Thread.java:745) 

This should not happen because rowKey="#{row.fruitId}" used with this <p:dataTable> .

The exception disappears only when the rowKey attribute rowKey removed, and the getRowKey() and getRowData() methods are implemented in the associated managed bean as follows.

 @Override public Object getRowKey(Fruit fruit) { return fruit != null ? fruit.getFruitId() : null; } @Override public Fruit getRowData(String rowKey) { List<Fruit> fruits = (List<Fruit>) getWrappedData(); Integer value = Integer.valueOf(rowKey); for (Fruit fruit : fruits) { if (fruit.getFruitId().equals(value)) { return fruit; } } return null; } 

Is it mandatory in the latest version of PrimeFaces (5.2 final), which is not needed in the previous version of PrimeFaces (end 5.1)?

Tested on Mojarra 2.3.0-m02. I suggested that there should be nothing to do with this version of Mojara.

+7
jsf primefaces
source share
1 answer

As mentioned in this link pointing to the PrimeFaces community forum,

We changed this design part to handle the rowKey attribute with LazyDataModel incorrectly.

The two methods getRowKey() and getRowData() should be implemented in a related managed bean when the LazyDataModel<T> used, as shown in the question.

From the PrimeFaces User Guide (PDF) - (5.1 (p. 164) and 5.2 (p. 166)):

Lazy Loading is an approach to the efficient use of huge data sets, regular ajax-based animation works by rendering only a specific one but still requires that all data be loaded into memory. lazy loading a datatable makes a specific page similar, but it does not load the page data into memory as well. To do this, you need to bind org.primefaces.model.LazyDataModel as the value and load of the implementation method and enable the lazy option. You also need to implement getRowData and getRowKey if you have a choice.


The rowKey attribute can be used when lazy disabled - set to false (default), and row selection is enabled.

From the PrimeFaces User Guide (PDF) - (5.1 (p. 159) and 5.2 (p. 161)):

RowKey must have a unique identifier from your data model and be used by datatable to find the selected rows. You can define this key using the rowKey attribute or by binding a data model that implements org.primefaces.model.SelectableDataModel .

For example,

 <p:dataTable var="car" value="#{carBean.cars}" selection="#{carBean.selectedCars}" rowKey="#{car.id}"> <p:column selectionMode="multiple"/> <!--columns--> </p:dataTable> 
+5
source share

All Articles