getRowData and getRowKey never executed LazyDataModel - jsf

I tried many things know. This thread is related to another thread but now the problem is more specific. I found out that the methods getRowData() and also if I implement it getRowKey() don't get called.
What I've tried:
In my .xhtml I set the rowKey and it's fine. No Compiler Error. In the Controller I write down the getRowData(). I try to select something and this breaks the whole page. The setter doesn't get called. If I don't overwrite getRowData() the compiler still works.
When I try to implement getRowKey() and getRowData() in my Controller it tells me ... exception [getRowKey(T object) must be implemented by ...
Then I tried to implement SelectableDataModel to look if there is any difference but there's not.
When I delete the selectionMode so the whole selection everything is fine. Pagination works great. Also editing columns works. But my contextMenu which is needed to delete an entry does not work.
xhtml:
<h:form id="eintraegeList">
<p:panel header="Liste aller Einträge">
<p:dataTable id="table"
var="telefonbuch"
lazy="true"
widgetVar="tableWv"
value="#{telefonbuchList.lazyModel}"
editable="true"
resizableColumns="true"
liveResize="true"
style="margin-bottom:20px"
paginator="true"
rows="#{telefonbuchList.pageSize}"
emptyMessage="Keine Telefonbucheinträge vorhanden"
selectionMode="single"
selection="#{telefonbuchList.selectedEntry}"
rowKey="#{telefonbuch.id}"
currentPageReportTemplate="{startRecord}-{endRecord} von {totalRecords}"
paginatorTemplate="{RowsPerPageDropdown} {FirstPageLink} {PreviousPageLink} {CurrentPageReport} {NextPageLink} {LastPageLink}"
rowsPerPageTemplate="5,8,10">
<f:facet name="header">
<p:commandButton id="toggler" type="button" value="Anzeige" style="float:right" icon="pi pi-align-justify" />
<p:columnToggler datasource="table" trigger="toggler" />
</f:facet>
<p:ajax event="rowEdit" listener="#{telefonbuchList.onRowEdit}" update="table" />
<p:ajax event="rowEditCancel" listener="#{telefonbuchList.onRowCancel}" update="table" />
<p:ajax event="cellEdit" listener="#{telefonbuchList.onCellEdit}" update="table" />
<p:ajax event="rowSelect" listener="#{telefonbuchList.onRowSelect}" update="table" />
<p:separator />
<p:column headerText="ID" sortBy="#{telefonbuch.id}">
<h:outputText value="#{telefonbuch.id}" />
</p:column>
<p:column headerText="Vorname" sortBy="#{telefonbuch.vorname}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.vorname}" /></f:facet>
<f:facet name="input"><p:inputText id="vornameInput" value="#{telefonbuch.vorname}" style="width:100%"/></f:facet>
</p:cellEditor>
</p:column>
<p:column headerText="Nachname" sortBy="#{telefonbuch.nachname}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.nachname}" /></f:facet>
<f:facet name="input"><p:inputText id="nachnameInput" value="#{telefonbuch.nachname}" style="width:100%"/></f:facet>
</p:cellEditor>
</p:column>
<p:column headerText="Telefonnummer" sortBy="#{telefonbuch.telefonnummer}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.telefonnummer}" /></f:facet>
<f:facet name="input"><p:inputText id="telefonnummerInput" value="#{telefonbuch.telefonnummer}" style="width:100%"/></f:facet>
</p:cellEditor>
</p:column>
<p:column headerText="Handynummer" sortBy="#{telefonbuch.handynummer}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.handynummer}" /></f:facet>
<f:facet name="input"><p:inputText id="handynummerInput" value="#{telefonbuch.handynummer}" style="width:100%"/></f:facet>
</p:cellEditor>
</p:column>
<p:column headerText="Geschäftsstelle" sortBy="#{telefonbuch.geschaeftsstelle}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.geschaeftsstelle}" /></f:facet>
<f:facet name="input">
<p:selectOneMenu value="#{telefonbuch.geschaeftsstelle}" style="width:100%">
<f:selectItems value="#{telefonbuchController.geschaeftsstellen}" var="c" itemLabel="#{geschaeftsstelle}" itemValue="#{geschaeftsstelle}"/>
</p:selectOneMenu>
</f:facet>
</p:cellEditor>
</p:column>
<p:column headerText="Geschlecht" sortBy="#{telefonbuch.gender.shortGender}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.gender.shortGender}" /></f:facet>
<f:facet name="input">
<p:selectOneMenu id="gender" value="#{telefonbuch.gender}" style="width:100%">
<f:selectItem itemLabel="Keine Angabe" itemValue="" />
<f:selectItems value="#{telefonbuch.genders}" var="gender" itemLabel="#{gender.shortGender}" itemValue="#{gender}"/>
</p:selectOneMenu>
</f:facet>
</p:cellEditor>
</p:column>
<p:column exportable="false" style="width:20px;text-align:center;">
<p:rowEditor />
</p:column>
</p:dataTable>
<p:growl id="growl" showDetail="true" for="eintraege-list">
<p:autoUpdate />
</p:growl>
<p:separator />
<p:contextMenu for="table">
<p:menuitem value="Löschen" update="table" icon="fas fa-eraser" action="#{telefonbuchList.deleteEntry}"/>
<p:menuitem value="Edit Cell" icon="pi pi-search" onclick="PF('tableWv').showCellEditor();return false;"/>
</p:contextMenu>
</p:panel>
</h:form>
Controller:
#Scope(value = "session")
#Component(value = "telefonbuchList")
#ELBeanName(value = "telefonbuchList")
#Join(path = "/", to = "/eintraege-liste.jsf")
public class TelefonbuchListController extends LazyDataModel<Telefonbuch> {
private static final long serialVersionUID = 1L;
#Autowired
private TelefonbuchRepository telefonbuchRepository;
private List<Telefonbuch> selectedEntries;
private Telefonbuch selectedEntry;
private LazyDataModel<Telefonbuch> lazyModel;
private int pageSize = 5;
public void deleteEntry() {
telefonbuchRepository.deleteAll(selectedEntries);
lazyModel.getWrappedData().removeAll(selectedEntries);
selectedEntries.clear();
}
public LazyDataModel<Telefonbuch> getLazyModel() {
return lazyModel;
}
#Override
public int getPageSize() {
return pageSize;
}
#Override
public Telefonbuch getRowData(String rowKey) {
System.out.println("rowKey: " + rowKey);
List<Telefonbuch> list = getWrappedData();
for (Telefonbuch telefonbuch : list) {
if (telefonbuch.getId().toString().equals(rowKey)) {
return telefonbuch;
}
}
return null;
}
#Override
public Object getRowKey(Telefonbuch telefonbuch) {
return telefonbuch != null ? telefonbuch.getId() : null;
}
public List<Telefonbuch> getSelectedEntries() {
return selectedEntries;
}
public Telefonbuch getSelectedEntry() {
return selectedEntry;
}
#Deferred
#RequestAction
#IgnorePostback
public void loadData() {
lazyModel = new LazyDataModel<Telefonbuch>() {
private static final long serialVersionUID = 1L;
#Override
public List<Telefonbuch> load(int first, int pageSize, String sortField, SortOrder sortOrder,
Map<String, Object> filters) {
List<Telefonbuch> result = new ArrayList<Telefonbuch>();
if (first == 0) {
if (sortField != null && !sortField.isEmpty()) {
if (sortOrder.name().equalsIgnoreCase("ascending")) {
result = telefonbuchRepository
.findAll(PageRequest.of(first, pageSize, Sort.by(sortField).ascending()))
.getContent();
} else if (sortOrder.name().equalsIgnoreCase("descending")) {
result = telefonbuchRepository
.findAll(PageRequest.of(first, pageSize, Sort.by(sortField).descending()))
.getContent();
}
} else {
result = telefonbuchRepository.findAll(PageRequest.of(first, pageSize)).getContent();
}
} else {
first = first / pageSize;
if (sortField != null && !sortField.isEmpty()) {
if (sortOrder.name().equalsIgnoreCase("ascending")) {
result = telefonbuchRepository
.findAll(PageRequest.of(first, pageSize, Sort.by(sortField).ascending()))
.getContent();
} else if (sortOrder.name().equalsIgnoreCase("descending")) {
result = telefonbuchRepository
.findAll(PageRequest.of(first, pageSize, Sort.by(sortField).descending()))
.getContent();
}
} else {
result = telefonbuchRepository.findAll(PageRequest.of(first, pageSize)).getContent();
}
}
return result;
}
};
lazyModel.setRowCount((int) telefonbuchRepository.count()); // Aufruf auslagern, aber bei gemeinsamen Arbeiten kann neue Row hinzukommen
lazyModel.setPageSize(pageSize);
}
public void onCellEdit(CellEditEvent event) {
Object oldValue = event.getOldValue();
Object newValue = event.getNewValue();
telefonbuchRepository.save((Telefonbuch) newValue);
}
public void onRowEdit(RowEditEvent event) {
Object oldValue = event.getObject();
telefonbuchRepository.save((Telefonbuch) oldValue);
FacesMessage msg = new FacesMessage("Eintrag geändert",
((Telefonbuch) event.getObject()).getVorname() + " " + ((Telefonbuch) event.getObject()).getNachname());
FacesContext.getCurrentInstance().addMessage("eintraege-list", msg);
}
public void onRowSelect(SelectEvent event) {
FacesMessage msg = new FacesMessage("Eintrag ausgewählt",
((Telefonbuch) event.getObject()).getVorname() + " " + ((Telefonbuch) event.getObject()).getNachname());
FacesContext.getCurrentInstance().addMessage("eintraege-list", msg);
}
#Override
public void setPageSize(int pageSize) {
this.pageSize = pageSize;
}
public void setSelectedEntries(List<Telefonbuch> selectedEntries) {
this.selectedEntries = selectedEntries;
}
public void setSelectedEntry(Telefonbuch selectedEntry) {
this.selectedEntry = selectedEntry;
}
Model:
#Data
#Entity
public class Telefonbuch {
public enum Gender {
MALE("Männlich"), FEMALE("Weiblich");
private String shortGender;
private Gender(String shortGender) {
this.shortGender = shortGender;
}
public String getShortGender() {
return shortGender;
}
}
#Column
#Enumerated(EnumType.STRING)
private Gender gender;
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
#Column
private String vorname;
#Column
private String nachname;
#Column
private String telefonnummer;
#Column
private String handynummer;
#Column
private String geschaeftsstelle;
protected Telefonbuch() {
}
public Telefonbuch(String vorname, String nachname, String telefonnummer, String handynummer) {
this.vorname = vorname;
this.nachname = nachname;
this.telefonnummer = telefonnummer;
this.handynummer = handynummer;
}
PrimeFaces Version 6.2
JSF MyFaces Version 2.2.12
Java 1.8
Spring Boot 2.1.3

In your method
TelefonbuchListController.loadData() {
lazyModel = new LazyDataModel<Telefonbuch>() {
//...
}
you create a new anonymous instance of the abstract class LazyDataModel. This is then assigned to the lazyModel field which is later returned to your p:dataTable value attribute.
Obviously it does not override the non operative getRowKey nor getRowData methods from the abstract class LazyDataModel.
You will have to override them like this:
public void loadData() {
lazyModel = new LazyDataModel<Telefonbuch>() {
// ...
#Override
public Telefonbuch getRowData(String rowKey) {
// your implementation here
}
#Override
public Object getRowKey(Telefonbuch telefonbuch) {
// your implementation here
}
// ...
}
Both methods getRowKey and getRowData you presented in your questions belong to a LazyDataModel implementaion that is not assigned to the p:dataTable value attribute. Hence both never get invoked. If it was the LazyDataModel assigned to the p:dataTable value attribute, your p:dataTable would probably look somehow like this:
<p:dataTable id="table"
var="telefonbuch"
lazy="true"
widgetVar="tableWv"
value="#{telefonbuchList}"
...

Related

After adding LazyDataModel Editing and Delete not working

I didn't found a good answer so this problem. Maybe I just need to understand how to handle it. I implemented via contextMenu a menuItem to delete selected rows. That doesn't work anymore. Furthermore the editing does not working anymore. I have implemented a row editor. When I click on it, it gets activated and i can start editing but when I press okay or abort nothing happens.
No method is getting called. Not for deleting, not for editing, not even for selecting. It has obviously something to do with the lazyDataModel but how can I change it.
My Controller:
#Scope(value = "session")
#Component(value = "telefonbuchList")
#ELBeanName(value = "telefonbuchList")
#Join(path = "/", to = "/eintraege-liste.jsf")
public class TelefonbuchListController extends LazyDataModel<Telefonbuch> {
private static final long serialVersionUID = 1L;
#Autowired
private TelefonbuchRepository telefonbuchRepository;
private List<Telefonbuch> selectedEntries;
private LazyDataModel<Telefonbuch> lazyModel;
private int pageSize = 5;
public void deleteEntry() {
telefonbuchRepository.deleteAll(selectedEntries);
lazyModel.getWrappedData().removeAll(selectedEntries);
selectedEntries.clear();
}
public LazyDataModel<Telefonbuch> getLazyModel() {
return lazyModel;
}
#Override
public int getPageSize() {
return pageSize;
}
#Override
public Telefonbuch getRowData(String rowKey) {
List<Telefonbuch> list = getWrappedData();
for (Telefonbuch telefonbuch : list) {
if (telefonbuch.getId().toString().equals(rowKey)) {
return telefonbuch;
}
}
return null;
}
#Override
public Object getRowKey(Telefonbuch telefonbuch) {
return telefonbuch != null ? telefonbuch.getId() : null;
}
public List<Telefonbuch> getSelectedEntries() {
return selectedEntries;
}
#Deferred
#RequestAction
#IgnorePostback
public void loadData() {
lazyModel = new LazyDataModel<Telefonbuch>() {
private static final long serialVersionUID = 1L;
#Override
public List<Telefonbuch> load(int first, int pageSize, String sortField, SortOrder sortOrder,
Map<String, Object> filters) {
List<Telefonbuch> result = new ArrayList<Telefonbuch>();
if (first == 0) {
if (sortField != null && !sortField.isEmpty()) {
if (sortOrder.name().equalsIgnoreCase("ascending")) {
result = telefonbuchRepository
.findAll(PageRequest.of(first, pageSize, Sort.by(sortField).ascending()))
.getContent();
} else if (sortOrder.name().equalsIgnoreCase("descending")) {
result = telefonbuchRepository
.findAll(PageRequest.of(first, pageSize, Sort.by(sortField).descending()))
.getContent();
}
} else {
result = telefonbuchRepository.findAll(PageRequest.of(first, pageSize)).getContent();
}
} else {
first = first / pageSize;
if (sortField != null && !sortField.isEmpty()) {
if (sortOrder.name().equalsIgnoreCase("ascending")) {
result = telefonbuchRepository
.findAll(PageRequest.of(first, pageSize, Sort.by(sortField).ascending()))
.getContent();
} else if (sortOrder.name().equalsIgnoreCase("descending")) {
result = telefonbuchRepository
.findAll(PageRequest.of(first, pageSize, Sort.by(sortField).descending()))
.getContent();
}
} else {
result = telefonbuchRepository.findAll(PageRequest.of(first, pageSize)).getContent();
}
}
return result;
}
};
lazyModel.setRowCount((int) telefonbuchRepository.count());
lazyModel.setPageSize(pageSize);
}
public void onCellEdit(CellEditEvent event) {
Object oldValue = event.getOldValue();
Object newValue = event.getNewValue();
telefonbuchRepository.save((Telefonbuch) newValue);
}
public void onRowCancel(RowEditEvent event) {
}
public void onRowEdit(RowEditEvent event) {
Object oldValue = event.getObject();
telefonbuchRepository.save((Telefonbuch) oldValue);
FacesMessage msg = new FacesMessage("Eintrag geändert",
((Telefonbuch) event.getObject()).getVorname() + " " + ((Telefonbuch) event.getObject()).getNachname());
FacesContext.getCurrentInstance().addMessage("eintraege-list", msg);
}
#Override
public void setPageSize(int pageSize) {
this.pageSize = pageSize;
}
public void setSelectedEntries(List<Telefonbuch> selectedEntries) {
this.selectedEntries = selectedEntries;
}
The .xhtml:
<h:form id="eintraegeList">
<p:panel header="Liste aller Einträge">
<p:dataTable id="table" var="telefonbuch" lazy="true" widgetVar="tableWv" value="#{telefonbuchList.lazyModel}" stickyHeader="true" editable="true" resizableColumns="true" liveResize="true" style="margin-bottom:20px" paginator="true" rows="#{telefonbuchList.pageSize}" dynamic="true" emptyMessage="Keine Telefonbucheinträge vorhanden" selection="#{telefonbuchList.selectedEntries}" selectionMode="multiple" rowKey="#{telefonbuch.id}"
currentPageReportTemplate="{startRecord}-{endRecord} von {totalRecords}"
paginatorTemplate="{RowsPerPageDropdown} {FirstPageLink} {PreviousPageLink} {CurrentPageReport} {NextPageLink} {LastPageLink} {Exporters}"
rowsPerPageTemplate="5,8,10">
<f:facet name="header">
<p:commandButton id="toggler" type="button" value="Anzeige" style="float:right" icon="pi pi-align-justify" />
<p:columnToggler datasource="table" trigger="toggler" />
</f:facet>
<p:ajax event="rowEdit" listener="#{telefonbuchList.onRowEdit}" update="table" />
<p:ajax event="rowEditCancel" listener="#{telefonbuchList.onRowCancel}" update="table" />
<p:ajax event="cellEdit" listener="#{telefonbuchList.onCellEdit}" update="table" />
<p:separator />
<p:column headerText="ID" sortBy="#{telefonbuch.id}">
<h:outputText value="#{telefonbuch.id}" />
</p:column>
<p:column headerText="Vorname" sortBy="#{telefonbuch.vorname}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.vorname}" /></f:facet>
<f:facet name="input"><p:inputText id="vornameInput" value="#{telefonbuch.vorname}" style="width:100%"/></f:facet>
</p:cellEditor>
</p:column>
<p:column headerText="Nachname" sortBy="#{telefonbuch.nachname}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.nachname}" /></f:facet>
<f:facet name="input"><p:inputText id="nachnameInput" value="#{telefonbuch.nachname}" style="width:100%"/></f:facet>
</p:cellEditor>
</p:column>
<p:column headerText="Telefonnummer" sortBy="#{telefonbuch.telefonnummer}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.telefonnummer}" /></f:facet>
<f:facet name="input"><p:inputText id="telefonnummerInput" value="#{telefonbuch.telefonnummer}" style="width:100%"/></f:facet>
</p:cellEditor>
</p:column>
<p:column headerText="Handynummer" sortBy="#{telefonbuch.handynummer}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.handynummer}" /></f:facet>
<f:facet name="input"><p:inputText id="handynummerInput" value="#{telefonbuch.handynummer}" style="width:100%"/></f:facet>
</p:cellEditor>
</p:column>
<p:column headerText="Geschäftsstelle" sortBy="#{telefonbuch.geschaeftsstelle}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.geschaeftsstelle}" /></f:facet>
<f:facet name="input">
<p:selectOneMenu value="#{telefonbuch.geschaeftsstelle}" style="width:100%">
<f:selectItems value="#{telefonbuchController.geschaeftsstellen}" var="c" itemLabel="#{geschaeftsstelle}" itemValue="#{geschaeftsstelle}"/>
</p:selectOneMenu>
</f:facet>
</p:cellEditor>
</p:column>
<p:column headerText="Geschlecht" sortBy="#{telefonbuch.gender.shortGender}">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{telefonbuch.gender.shortGender}" /></f:facet>
<f:facet name="input">
<p:selectOneMenu id="gender" value="#{telefonbuch.gender}" style="width:100%">
<f:selectItem itemLabel="Keine Angabe" itemValue="" />
<f:selectItems value="#{telefonbuch.genders}" var="gender" itemLabel="#{gender.shortGender}" itemValue="#{gender}"/>
</p:selectOneMenu>
</f:facet>
</p:cellEditor>
</p:column>
<p:column style="width:20px;text-align:center;">
<p:rowEditor />
</p:column>
</p:dataTable>
<p:growl id="growl" showDetail="true" for="eintraege-list">
<p:autoUpdate />
</p:growl>
<p:separator />
<p:contextMenu for="table">
<h:outputStylesheet library="webjars" name="font-awesome/5.7.1/css/fontawesome.min-jsf.css" />
<p:menuitem value="Löschen" update="table" icon="fas fa-eraser" action="#{telefonbuchList.deleteEntry}"/>
<p:menuitem value="Edit Cell" icon="pi pi-search" onclick="PF('tableWv').showCellEditor();return false;"/>
</p:contextMenu>
<h3>Exportieren der Daten</h3>
<h:commandLink>
<p:graphicImage value="/img/icon-pdf.png" />
<p:dataExporter type="pdf" target="table" fileName="Telefonbuch" />
</h:commandLink>
</p:panel>
</h:form>
Model (Telefonbuch):
public enum Gender {
MALE("Männlich"), FEMALE("Weiblich");
private String shortGender;
private Gender(String shortGender) {
this.shortGender = shortGender;
}
public String getShortGender() {
return shortGender;
}
}
#Column
#Enumerated(EnumType.STRING)
private Gender gender;
#Id
#GeneratedValue(strategy = GenerationType.AUTO)
private Long id;
#Column
private String vorname;
#Column
private String nachname;
#Column
private String telefonnummer;
#Column
private String handynummer;
#Column
private String geschaeftsstelle;
PrimeFaces Version 6.2
JSF MyFaces Version 2.2.12
Java 1.8
Spring Boot 2.1.2

onRowSelect update second lazy p:datatable with new data

I hope someone will give me some hint about my problem. I have two <p:dataTable> that have lazy load. On first <p:dataTable> user can select row. According to selected row second <p:dataTable> must be updated with new lazy data (lazyModel2).
I don't know how to get new lazyModel2 and update second <p:dataTable> with new data on row select. onRowSelect event is working and I can get selectedRow data.
I just don't have any idea how to get new lazyModel2 from onRowSelect() method.
XHTML
<p:dataTable id="dt1"
var="dtVar1"
value="#{controller.lazyModel1}"
lazy="true"
rowKey="#{dtVar1.recordId}"
filterEvent="enter"
sortMode="multiple"
selectionMode="single"
selection="#{controller.selected1item}">
<p:ajax event="rowSelect"listener="#{controller.onRowSelect}"update="MasterForm:dt2"/>
<p:column headerText="Text" sortBy="#{dtVar1.text}" filterBy="#{dtVar1.text}" style="width: 100px">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{dtVar1.text}"/></f:facet>
<f:facet name="input"><p:inputText value="#{dtVar1.text}"style="width: 100%"/></f:facet>
</p:cellEditor>
</p:column>
...
</p:dataTable>
<p:dataTable id="dt2"
var="dtVar2"
value="#{controller.lazyModel2}"
lazy="true"
rowKey="#{dtVar2.recordId}"
filterEvent="enter"
sortMode="multiple"
editable="true"
editMode="row">
<p:ajax event="rowEdit" listener="#{controller.onRowEdit}" update="dt2"/>
<p:column style="width: 32px">
<f:facet name="header"><h:outputText value=""/></f:facet>
<p:rowEditor/>
</p:column>
<p:column headerText="Text 2" sortBy="#{dtVar2.konto}" filterBy="#{dtVar2.konto}" style="width: 100px">
<p:cellEditor>
<f:facet name="output"><h:outputText value="#{dtVar2.konto}"/></f:facet>
<f:facet name="input"><p:inputText value="#{dtVar2.konto}" style="width: 100%"/></f:facet>
</p:cellEditor>
</p:column>
...
</p:dataTable>
CONTROLLER
#Named
#ViewScoped
public class Controller extends GenericWebController {
#Inject
private Lazy1DataModel lazyModel1;
#Inject
private Lazy2DataModel lazyModel2;
public void onRowSelect(SelectEvent event) throws SQLException {
...
filters.put("recordId", arraylistafiltera);
...
List<FPromInDto> newlazy = getLazyModel2().load(0,15,null, filters);
lazyModel2.setWrappedData(newlazy);
}
public Lazy1DataModel getLazyModel1() { return lazyModel1; }
public void setLazyModel1(Lazy1DataModel lazyModel1) { this.lazyModel1 = lazyModel1; }
public Lazy2DataModel getLazyModel2() { return lazyModel2; }
public void setLazyModel2(Lazy2DataModel lazyModel2) { this.lazyModel2 = lazyModel2; }
}
Lazy2DataModel
public class Lazy2DataModel extends LazyDataModel<SomeDto> {
#Inject
private SomeDao someDao;
#Override
public List<SomeDto> load(int first, int pageSize, List<SortMeta> multiSortMeta, Map<String, Object> filters) {
List<SomeDto> data = new ArrayList<>();
try {
data = someDao.lazyLoad(first, pageSize, BiLazyUtils.getSortString(multiSortMeta, SomeDto.class), BiLazyUtils.getFilterString(filters, SomeDto.class));
this.setRowCount(someDao.count(BiLazyUtils.getFilterString(filters, SomeDto.class)));
} catch (SQLException e) {
e.printStackTrace();
}
return data;
}

setPropertyActionListener sets to null

I'm putting the currently iterated dataTable as a property of a managed bean using .Here I want to take one localproduct and send it to the dialog to change the values. But I did not add the code for that due to my setListener does not work and it does not set or it sets to null. However, it is always set it as null. Can selection mode kill the setPropertyActionListener?
The view, local-product.xhtml:
<ui:define name="content">
<h:form prependId="false" style="margin-top: 25px" id="form">
<p:dataTable id="tableData" value="#{localProductUI.localProductLazyModel}" var="localProduct" style="max-width: 1200px; margin-top: 20px;" paginator="true"
paginatorTemplate="{CurrentPageReport} {FirstPageLink} {PreviousPageLink} {PageLinks} {NextPageLink} {LastPageLink} {RowsPerPageDropdown}"
rowsPerPageTemplate="20,100,200,500" rows="20" lazy="true" rowIndexVar="row" editable="true" editMode="cell"
widgetVar="productTable" reflow="true" selection="#{localProductUI.selectedNewLocalProduct}" rowKey="#{localProduct.id}" rowSelectMode="checkbox">
<f:facet name="header">
<h:outputText value="Number of products: #{localProductUI.countProduct}" id="card-count"/>
</f:facet>
<p:column selectionMode="multiple" filterValue="" style="width: 20px"/>
<p:column headerText="Id" sortBy="#{localProduct.id}">
#{localProduct.id}
</p:column>
<p:column headerText="Name" filterBy="#{localProduct.name}" style="white-space: normal;">
#{localProduct.name}
</p:column>
<p:column headerText="Code" sortBy="#{localProduct.code}" filterBy="#{localProduct.code}">
#{localProduct.code}
</p:column>
<p:column headerText="Category" filterBy="#{localProduct.categoryId}" style="white-space: normal;">
#{localProduct.categoryId}
</p:column>
<p:column headerText="APrice" sortBy="#{localProduct.arrivalCost}">
#{util.fDouble(localProduct.arrivalCost)}
</p:column>
<p:column headerText="SPrice" sortBy="#{localProduct.sellingPrice}">
#{util.fDouble(localProduct.sellingPrice)}
</p:column>
<p:column headerText="Change">
<p:commandButton value="Change" update=":productDetail" onclick="PF('productDialog').show();"
action="#{localProductUI.editNewLocalProduct}" >
<f:setPropertyActionListener target="#{localProductUI.newLocalProduct}" value="#{localProduct}" />
</p:commandButton>
</p:column>
</p:dataTable>
<p:dialog header = "Change product" widgetVar="productDialog" modal="true" showEffect="fade" hideEffect="fade" resizable="false">
<p:outputPanel id="productDetail" style="text-align: center">
<p:panelGrid columns="2" rendered="#{not empty localProductUI.newLocalProduct}" columnClasses="label,value">
<h:outputText value="Name:"/>
<h:outputText value="#{localProductUI.newLocalProduct.name}"/>
<h:outputText value="Code:"/>
<h:outputText value="#{localProductUI.newLocalProduct.code}"/>
<h:outputText value="Category:"/>
<h:outputText value="#{localProductUI.newLocalProduct.categoryId}"/>
<h:outputText value="APrice:"/>
<h:outputText value="#{localProductUI.newLocalProduct.arrivalCost}"/>
<h:outputText value="SPrice:"/>
<h:outputText value="#{localProductUI.newLocalProduct.sellingPrice}"/>
</p:panelGrid>
</p:outputPanel>
</p:dialog>
</h:form>
</ui:define>
</ui:composition>
The managed bean, LocalProductUI:
public class LocalProductUI implements Serializable {
/*
* Consts
*/
private static final Logger log = Logger.getLogger(LocalProductUI.class.getName());
/*
* EJB
*/
#EJB private NewLocalProductEJB newLocalProductEJB;
/*
* Fields
*/
private LazyDataModel<NewLocalProduct> localProductLazyModel;
private Integer countProduct;
private List<NewLocalProduct> selectedNewLocalProduct;
private NewLocalProduct newLocalProduct;
/*
* Init
*/
public void init() {
this.localProductLazyModel = new LazyDataModel<NewLocalProduct>() {
#Override
public List<NewLocalProduct> load(int first, int pageSize, String sortField, SortOrder sortOrder, Map<String, Object> filters) {
localProductLazyModel.setRowCount(newLocalProductEJB.countNewLocalProducts(filters));
countProduct = newLocalProductEJB.countNewLocalProducts(filters);
Boolean sortAsc = sortOrder == null ? null : sortOrder == SortOrder.ASCENDING;
return newLocalProductEJB.getNewLocalProductList(first, pageSize, sortField, sortAsc, filters);
}
#Override
public NewLocalProduct getRowData(String rowKey) {
int id;
try {
id = new Integer(rowKey);
} catch (NumberFormatException e) {
throw new Error(e);
}
return newLocalProductEJB.findById(id);
}
#Override
public Object getRowKey(NewLocalProduct product) {
return product.getId();
}
#Override
public void setRowIndex(int rowIndex) {
if (rowIndex == -1 || getPageSize() == 0) {
super.setRowIndex(-1);
} else {
super.setRowIndex(rowIndex % getPageSize());
}
}
};
localProductLazyModel.setRowCount(newLocalProductEJB.countNewLocalProducts(new HashMap<String, Object>()));
}
/*
* Actions
*/
public void saveToGlobalProduct() throws InputValidationException {
newLocalProductEJB.doSave(selectedNewLocalProduct);
FacesMessage msg = new FacesMessage("Number of local products added: "+ selectedNewLocalProduct.size());
FacesContext.getCurrentInstance().addMessage(null,msg);
}
public void editNewLocalProduct(){
System.err.println("Change here!");
}
public void removeProduct() throws InputValidationException {
newLocalProductEJB.doRemove(selectedNewLocalProduct);
FacesMessage msg = new FacesMessage("Number of local products deleted: "+ selectedNewLocalProduct.size());
FacesContext.getCurrentInstance().addMessage(null,msg);
}
/*
* Getters/setters
*/
public Integer getCountProduct() { return countProduct; }
public void setCountProduct(Integer countProduct){
this.countProduct = countProduct;
}
public LazyDataModel<NewLocalProduct> getLocalProductLazyModel() { return localProductLazyModel; }
public void setLocalProductLazyModel(LazyDataModel<NewLocalProduct> localProductLazyModel){ this.localProductLazyModel = localProductLazyModel; }
public List<NewLocalProduct> getSelectedNewLocalProduct(){ return selectedNewLocalProduct; }
public void setSelectedNewLocalProduct(List<NewLocalProduct> selectedNewLocalProduct){ this.selectedNewLocalProduct = selectedNewLocalProduct; }
public NewLocalProduct getNewLocalProduct() { return newLocalProduct; }
public void setNewLocalProduct(NewLocalProduct newLocalProduct){ this.newLocalProduct = newLocalProduct;}
}

primefaces selectCheckboxMenu empty selected list

I'm trying to get selected values from a selectCheckboxMenu, but always the selection list is empty. this's my jsf form:
<h:form id="form">
<p:dataTable id="singleDT" var="user" value="#{roleBean.users}"
rowKey="#{roleBean.users}" rows="12" paginator="true"
rowsPerPageTemplate="12,15,22" paginatorPosition="bottom"
emptyMessage="Aucun compte présent." reflow="true"
editable="false" selectionMode="single">
<p:column headerText="Login" filterBy="#{user.username}">
<h:outputText value="#{user.username}" />
</p:column>
<p:column headerText="Nom" filterBy="#{user.lastname}">
<h:outputText value="#{user.lastname}" />
</p:column>
<p:column headerText="Prénom" filterBy="#{user.firstName}">
<h:outputText value="#{user.firstName}" />
</p:column>
<p:column headerText="Email" filterBy="#{user.emal}">
<h:outputText value="#{user.emal}" />
</p:column>
<p:column headerText="Affécter Roles">
<p:selectCheckboxMenu id="menu" value="#{roleBean.rolesselected}"
label="Roles"
filter="false" filterMatchMode="startsWith"
panelStyle="width:135px" converter="#{roleconvertor}" immediate="true" >
<f:selectItems value="#{roleBean.roles}" var="n"
itemValue="#{n}" itemLabel="#{n.description}"
itemDescription="#{n.rolename}" />
</p:selectCheckboxMenu>
</p:column>
<p:column width="90">
<p:commandButton styleClass="ui-yelbutton" immediate="true" process="#form" value="Valider"
title="Remove"
ajax="true" action="#{roleBean.addrole(user)}" />
</p:column>
</p:dataTable>
</h:form>
Here's the managedBean related. when I run the jsf page I show the list of value and I can check it. also tne converter was worked but when I try to test a size of selectedrole it's always 0.
public class RoleBean implements Serializable {
#Autowired
UserCatalogueService userservice;
#Autowired
Roleservice roleservice;
List< Role> roles;
List<UserCatalogue> users ;
private static final long serialVersionUID = 1L;
String notification;
private List<Role> rolesselected = new ArrayList<Role>();
#PostConstruct
public void init() {
roles=roleservice.findAll();
}
public List<Role> getRolesselected() {
return rolesselected;
}
public void setRolesselected(List<Role> rolesselected) {
this.rolesselected = rolesselected;
}
public List<UserCatalogue> getUsers() {
List<UserCatalogue> users= userservice.findAll();
List<UserCatalogue> users1= userservice.findAll();
users1.clear();
for(int i=0; i< users.size(); i++)
{
if(users.get(i).getRoles().size()==0)
{
System.out.println(users.get(i).getFirstName()+ "est un nouvel utilisateur");
//users.remove(i);
users1.add(users.get(i));
}
}
return users1;
}
public String getNotification() {
notification=getUsers().size()+" Alerts";
return notification;
}
public void setNotification(String notification) {
this.notification = notification;
}
public void setUsers(List<UserCatalogue> users) {
this.users = users;
}
public List<Role> getRoles() {
return roleservice.findAll();
}
public void setRoles(List<Role> roles) {
this.roles = roles;
}
public void addrole( UserCatalogue user)
{
System.out.println("the size of list is "+rolesselected.size());
}
}
Try to change rolesselected from List to array using the []

PrimeFaces showing one item of list on a row

I'm using datatable to retrieve records from database. Datatable is showing all the items on rows as expected. What I want is how to choose only a couple or single one of them, could it be by specifying the index of the item in datatable? or by the SQL query?
bean :
public JcalendarController getSelectedUser() {
return selectedday;
}
public void setSelectedUser(JcalendarController selectedday) {
this.selectedday = selectedday;
}
List<String> user_spinner_list = new ArrayList<String>();
List<JcalendarController> calendarlist = new ArrayList<JcalendarController>();
public void delete() {
System.out.println("JadminBeans >> delete() ---------- id= ");
JcalendarDAO.deleteDay(selectedday);
}
public List<JcalendarController> getMessages() {
System.out.println("List<JcalendarController> getMessages()");
calendarlist = JcalendarDAO.getdays();
return calendarlist;
}
public long getId() {
return id;
}
public void setId(long id) {
this.id = id;
}
public String getUsername() {
return username;
}
public void setUsername(String username) {
this.username = username;
}
public int getDay() {
return day;
}
public void setDay(int day) {
this.day = day;
}
public String getText() {
return text;
}
public void setText(String text) {
this.text = text;
}
public UploadedFile getFile() {
return file;
}
public void setFile(UploadedFile file) {
this.file = file;
}
//--------------------------------------------------------------------------
//---------------------------- user_spinner() ----------------------------//
public List<String> user_spinner() {
System.out.println("List<JcalendarBeans> user_spinner()");
user_spinner_list = JcalendarDAO.AllUsarname_spinner();
return user_spinner_list;
}
//---------------------------- ImageUpload() ----------------------------//
public void ImageUpload() {
JcalendarController CC = new JcalendarController(this.username, this.day, this.file);
System.out.println(this.username + " " + this.day + " " + this.file);
calendarlist.add(CC);
JcalendarDAO.add_image_DAO(CC);
}
//---------------------------- TextUpload() ----------------------------//
public void TextUpload() {
JcalendarController CC = new JcalendarController(this.username, this.day, this.text);
System.out.println(this.username + " " + this.day + " " + this.text);
calendarlist.add(CC);
JcalendarDAO.add_text_DAO(CC);
}
DAO :
public static List<JcalendarController> getdays() {
List<JcalendarController> ccs = new ArrayList<JcalendarController>();
try {
Statement statement = connection.createStatement();
ResultSet rs = statement.executeQuery("select * from calendar");
while (rs.next()) {
JcalendarController cc = new JcalendarController();
cc.setId(rs.getLong("id"));
cc.setDay(rs.getInt("day"));
cc.setText(rs.getString("text"));
cc.setUsername(rs.getString("username"));
}
} catch (SQLException e) {
e.printStackTrace();
}
return ccs;
}
XHTML
<p:dataTable value="#{Jcalendar.messages}" var="o" paginator="true" selection="#{Jcalendar.selectedUser}"
rowKey="#{o.id}" style="margin-bottom:20px"
paginatorTemplate="{CurrentPageReport} {FirstPageLink} {PreviousPageLink} {PageLinks} {NextPageLink} {LastPageLink} {RowsPerPageDropdown}"
rowsPerPageTemplate="24,48,144">
<f:facet name="header">
<h:outputText value="Data showing from database" />
</f:facet>
<p:column selectionMode="single" />
<p:column>
<f:facet name="header">
<h:outputText value=" Id" />
</f:facet>
<h:outputText value="#{o.id}" />
</p:column>
<p:column>
<f:facet name="header">
<h:outputText value="Day" />
</f:facet>
<h:outputText value="#{o.day}" />
</p:column>
<p:column>
<f:facet name="header">
<h:outputText value="Text" />
</f:facet>
<h:outputText value="#{o.text}" />
</p:column>
<p:column>
<f:facet name="header">
<h:outputText value="Username" />
</f:facet>
<h:outputText value="#{o.username}" />
</p:column>
<p:column>
<f:facet name="header">
<h:outputText value="Image" />
</f:facet>
<h:outputLink value="DisplayImage?id=#{o.id}" target="_blank">
<h:graphicImage value="DisplayImage?id=#{o.id}" width="50" height="50"></h:graphicImage>
</h:outputLink>
</p:column>
<f:facet name="footer">
<p:commandButton value="Delete" action="#{Jcalendar.delete()}" ajax="false" update=":form:msgs"/>
</f:facet>
</p:dataTable>
The datatable will show the values of the messages property, so whatever is in the list returned by the getMessages() will be rendered inside the table.
For what concerns you question, it is best to make a DAO method and return from the DB only the needed records, putting it in your words, use the SQL.
One optimization hint, you should avoid using any logic inside your getter methods as during the life-cycle of a single request, it can be called multiple times. In your case it would contact a DB upon every call. You can check this post to learn more, and find a better way to initialize your list.

Resources