jw90
May 17, 2019, 11:28am
#5
I tried your implementation, but I always got an error in my edit screen.
@Subscribe(target = Target.DATA_CONTEXT)
private void onPostCommit(DataContext.PostCommitEvent event) {
Entity committedEntity = event.getCommittedInstances().stream()
.filter(entity -> entity.equals(getEditedEntity()))
.findFirst()
.get();
Long id = ((EntityType) committedEntity).getId();
showMessageDialog("Test", "ID:" + id, MessageType.CONFIRMATION);
}
Error:
DevelopmentException: Unable to find @Subscribe target in vorgangsverwaltung$Vorgang.edit
I also tried this and got a NullPointerException:
@Inject
private DataContext dataContext;
dataContext.addPostCommitListener(event -> {
Entity committedEntity = event.getCommittedInstances().stream()
.filter(entity -> entity.equals(getEditedEntity()))
.findFirst()
.get();
Long id = ((EntityType) committedEntity).getId();
showMessageDialog("Test", "ID:" + id, MessageType.CONFIRMATION);
});
So in both cases the dataContext was not available.
Why is that? I checked online, but I could not find anything.
krivopustov
(Konstantin Krivopustov)
May 17, 2019, 1:33pm
#6
Please provide the whole source code of the screen controller and descriptor.
jw90
May 18, 2019, 10:49am
#7
It is quite a lot.
I hope you find what you need.
Edit screen descriptor:
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<window xmlns="http://schemas.haulmont.com/cuba/window.xsd" caption="msg://editorCaption"
class="de.nexloy.crm.vorgangsverwaltung.web.vorgang.VorgangEdit" datasource="vorgangDs"
messagesPack="de.nexloy.crm.vorgangsverwaltung.web.vorgang">
<dsContext>
<datasource id="vorgangDs" class="de.nexloy.crm.vorgangsverwaltung.entity.Vorgang" view="Vorgang-screen-view">
<datasource id="kndNrDs" property="kndNr"/>
<datasource id="filNrDs" property="filNr"/>
<datasource id="vorgangskategorieDs" property="vorgangskategorie"/>
<datasource id="kontaktgruppeDs" property="kontaktgruppe"/>
<datasource id="markeDs" property="marke"/>
<datasource id="artikelNrDs" property="artikelNr"/>
<datasource id="vorgangGruppeDs" property="vorgangGruppe"/>
</datasource>
<collectionDatasource id="artikelNrsDs" allowCommit="false"
class="de.nexloy.crm.vorgangsverwaltung.entity.Artkl" view="_minimal">
<query><![CDATA[select e from vorgangsverwaltung$Artkl e]]></query>
</collectionDatasource>
<collectionDatasource id="vorgangGruppesDs" allowCommit="false"
class="de.nexloy.crm.vorgangsverwaltung.entity.VorgangGruppe" view="_minimal">
<query><![CDATA[select e from vorgangsverwaltung$VorgangGruppe e
where e.istAktiv = 1]]></query>
</collectionDatasource>
<collectionDatasource id="vorgangskategoriesDs" allowCommit="false"
class="de.nexloy.crm.vorgangsverwaltung.entity.Vorgangskategorie"
view="vorgangskategorie-view">
<query><![CDATA[select e from vorgangsverwaltung$Vorgangskategorie e
where e.ist_aktiv = 1]]></query>
</collectionDatasource>
<collectionDatasource id="vorgangMarkesDs" allowCommit="false"
class="de.nexloy.crm.vorgangsverwaltung.entity.VorgangMarke" view="_minimal">
<query><![CDATA[select e from vorgangsverwaltung$VorgangMarke e]]></query>
</collectionDatasource>
<collectionDatasource id="vorgangKontaktgruppesDs" allowCommit="false"
class="de.nexloy.crm.vorgangsverwaltung.entity.VorgangKontaktgruppe" view="_minimal">
<query><![CDATA[select e from vorgangsverwaltung$VorgangKontaktgruppe e]]></query>
</collectionDatasource>
<collectionDatasource id="vorgangHistoriesDs" class="de.nexloy.crm.vorgangsverwaltung.entity.VorgangHistorie"
view="vorgangHistorie-full-view">
<query><![CDATA[select e from vorgangsverwaltung$VorgangHistorie e
where :ds$vorgangDs.id = e.vorgang.id
order by e.createTs desc]]></query>
</collectionDatasource>
<collectionDatasource id="kndKrtnsDs" allowCommit="false"
class="de.nexloy.crm.vorgangsverwaltung.entity.KndKrtn" view="kndKrtn-view">
<query><![CDATA[select e from vorgangsverwaltung$KndKrtn e
where e.id = :component$customerCardId]]></query>
</collectionDatasource>
<collectionDatasource id="filsDs" allowCommit="false" class="de.nexloy.crm.vorgangsverwaltung.entity.Fil"
view="Fil-screen-view">
<query><![CDATA[select e from vorgangsverwaltung$Fil e
where e.filstatus.id = 0]]></query>
</collectionDatasource>
<collectionDatasource id="artklSearchDs" allowCommit="false"
class="de.nexloy.crm.vorgangsverwaltung.entity.Artkl" view="Artkl-screen-view">
<query><![CDATA[select e from vorgangsverwaltung$Artkl e
where e.id like CONCAT(:custom$searchString,'%')]]></query>
</collectionDatasource>
<groupDatasource id="kndVorgangsDs" allowCommit="false" class="de.nexloy.crm.vorgangsverwaltung.entity.Vorgang"
view="Vorgang-screen-view">
<query><![CDATA[select e from vorgangsverwaltung$Vorgang e
where :ds$vorgangDs.kndNr.id = e.kndNr.id
order by e.id desc]]></query>
</groupDatasource>
</dsContext>
<layout spacing="true">
<scrollBox height="100%" margin="true">
<buttonsPanel height="50px" responsive="true">
<button id="btnSave" caption="msg://speichern" invoke="onBtnSaveClick" stylename="primary"/>
<button id="btnSaveAndClose" caption="msg://speichern_und_schliessen" invoke="onBtnSaveAndCloseClick"
stylename="primary"/>
<button id="btnSaveAndNew" caption="msg://speichern_und_neu" invoke="onBtnSaveAndNewClick"
stylename="friendly"/>
<button id="btnCancel" invoke="onBtnCancelClick" caption="msg://cancel" stylename="danger"/>
</buttonsPanel>
<hbox height="50px" margin="true,false,true,false" responsive="true" visible="false">
<frame height="35px" width="AUTO" align="MIDDLE_LEFT" screen="editWindowActions"/>
</hbox>
<tabSheet id="tabSheet">
<tab id="tab-general" caption="msg://allgemein" margin="true" spacing="true">
<vbox>
<flowBox>
<groupBox id="gbVorgang" caption="msg://vorgang" height="540px" outerMargin="true"
settingsEnabled="false" width="AUTO">
<textField id="id" caption="msg://vorgang_id" datasource="vorgangDs" datatype="long"
editable="false" property="id"/>
<textField id="tfKontaktperson" caption="msg://kontaktperson" datasource="vorgangDs"
datatype="string" property="kontaktperson" width="350px"/>
<textField id="tfContactInfo" caption="msg://kontaktinfo" datasource="vorgangDs"
datatype="string" property="kontaktinfo" width="350px"/>
<lookupPickerField id="lpfFilNr" caption="msg://filNr" datasource="vorgangDs"
optionsDatasource="filsDs" property="filNr" width="350px">
<actions>
<action id="lookup"/>
</actions>
</lookupPickerField>
<lookupField id="lfContactType" caption="msg://kontaktart" datasource="vorgangDs"
optionsEnum="de.nexloy.crm.vorgangsverwaltung.entity.Kontaktart"
property="kontaktart" required="true" width="350px"/>
<optionsGroup id="ogContactDirection" caption="msg://kontaktrichtung"
datasource="vorgangDs"
optionsEnum="de.nexloy.crm.vorgangsverwaltung.entity.Kontaktrichtung"
orientation="horizontal" property="kontaktrichtung" visible="false"/>
<lookupField id="lfProcessGroup" caption="msg://vorgangsgruppe" datasource="vorgangDs"
optionsDatasource="vorgangGruppesDs" property="vorgangGruppe" width="350px"
required="true"/>
<lookupField id="lfProcessCategory" caption="msg://vorgangskategorie"
datasource="vorgangDs" optionsDatasource="vorgangskategoriesDs"
property="vorgangskategorie" width="350px" required="true"/>
<textField id="tfSubject" datasource="vorgangDs" property="bezug" width="350px"
caption="msg://bezug" datatype="string"/>
<lookupField id="lfStatus" caption="msg://status" datasource="vorgangDs"
optionsEnum="de.nexloy.crm.vorgangsverwaltung.entity.Status"
property="status" width="350px"/>
<dateField id="dfDeadline" caption="msg://terminAm" datasource="vorgangDs"
dateFormat="msg://dateFormat" property="terminAm" width="350px"/>
</groupBox>
<groupBox id="gbDesc" caption="msg://beschreibung" height="540px" outerMargin="true"
settingsEnabled="false" visible="false" width="750px">
<richTextArea id="rtfDesc" height="100%" width="100%"/>
</groupBox>
<groupBox id="gbKunde" caption="msg://kunde" height="540px" outerMargin="true"
settingsEnabled="false" width="AUTO">
<vbox spacing="true">
<textField id="customerCardId" caption="msg://customerCardId" datatype="long"
width="350px"/>
<pickerField id="customerId" caption="msg://kndNr" datasource="vorgangDs"
property="kndNr" width="350px">
<actions>
<action id="lookup"/>
<action id="clear"/>
<action id="open"/>
</actions>
</pickerField>
</vbox>
</groupBox>
<groupBox id="GbHistory" height="540px" width="750px" outerMargin="true" settingsEnabled="false">
<dataGrid id="vorgangshistorieDataGrid" columnsCollapsingAllowed="false"
datasource="vorgangHistoriesDs" height="100%" width="100%">
<actions>
<action id="create" caption="msg://neu"/>
<action id="refresh"/>
<action id="edit" caption="msg://bearbeiten"/>
<action id="refresh" caption="msg://refresh"/>
</actions>
<columns>
<column id="createTs" caption="msg://createTs" editable="false"
property="createTs"/>
<column id="createdBy" caption="msg://createdBy" editable="false"
property="createdBy"/>
</columns>
<buttonsPanel>
<button id="createDataGridBtn" action="vorgangshistorieDataGrid.create"
caption="msg://neu" icon="icons/plus-btn.png"/>
<button id="saveDataGridBtn" action="vorgangshistorieDataGrid.edit"/>
<button id="refreshDataGridBtn" action="vorgangshistorieDataGrid.refresh"/>
</buttonsPanel>
</dataGrid>
</groupBox>
</flowBox>
</vbox>
</tab>
<tab id="markenTab" caption="msg://eigenmarke" margin="true" spacing="true">
<searchPickerField id="spArticleNr" caption="msg://artikel" datasource="vorgangDs"
property="artikelNr" width="350px" minSearchStringLength="1"
optionsDatasource="artklSearchDs">
<actions>
<action id="lookup" type="picker_lookup"/>
<action id="open" type="picker_open"/>
</actions>
</searchPickerField>
<textField caption="msg://artikelInfo" datasource="vorgangDs" property="artikelInfo" width="350px"/>
<lookupPickerField id="lpBrand" caption="msg://marke" datasource="vorgangDs"
optionsDatasource="vorgangMarkesDs" property="marke" width="350px">
<actions>
<action id="lookup" type="picker_lookup"/>
<action id="open" type="picker_open"/>
</actions>
</lookupPickerField>
<lookupField caption="msg://kontaktgruppe" datasource="vorgangDs"
optionsDatasource="vorgangKontaktgruppesDs" property="kontaktgruppe" width="350px"/>
<textArea caption="msg://anliegen" datasource="vorgangDs" maxLength="4000" property="anliegen"
width="350px"/>
<optionsGroup caption="msg://rueckmeldung" datasource="vorgangDs"
optionsEnum="de.nexloy.crm.vorgangsverwaltung.entity.JaNein" orientation="horizontal"
property="rueckmeldungErwuenscht" width="350px" required="true"/>
<optionsGroup caption="msg://exportSperre" datasource="vorgangDs"
optionsEnum="de.nexloy.crm.vorgangsverwaltung.entity.JaNein" orientation="horizontal"
property="exportSperre" width="350px" required="true"/>
<dateField id="dfExportDatum" caption="msg://exportDatum" datasource="vorgangDs" editable="false"
enable="false" property="exportDatum"/>
</tab>
<tab id="kndVorgaengeTab" caption="msg://kndVorgaenge" margin="true,false,false,false" spacing="true"
visible="false">
<groupTable id="groupTableKndVorgaenge" height="100%" width="100%">
<actions>
<action id="edit" openType="NEW_TAB"/>
</actions>
<columns>
<column id="id" caption="msg://vorgang_id"/>
<column id="kontaktart" caption="msg://kontaktart"/>
<column id="kontaktgruppe" caption="msg://kontaktgruppe"/>
<column id="vorgangskategorie" caption="msg://vorgangskategorie"/>
<column id="filNr" caption="msg://filiale"/>
<column id="bezug" caption="msg://bezug"/>
<column id="status" caption="msg://status"/>
<column id="angelegtVon" caption="msg://angelegtVon"/>
<column id="angelegtAm" caption="msg://angelegtAm"/>
<column id="geaendertVon" caption="msg://geaendertVon"/>
<column id="geaendertAm" caption="msg://geaendertAm"/>
</columns>
<rows datasource="kndVorgangsDs"/>
<buttonsPanel>
<button caption="msg://bearbeiten" action="groupTableKndVorgaenge.edit"/>
</buttonsPanel>
</groupTable>
</tab>
<tab id="exportTab" caption="msg://Export" margin="true" spacing="true">
<groupBox id="gbVorgangsexport" caption="msg://Vorgangsexport" outerMargin="true" spacing="true">
<button id="exportButton" caption="msg://Export" invoke="onExportButtonClick" icon="PRINT"/>
</groupBox>
</tab>
</tabSheet>
</scrollBox>
</layout>
</window>
jw90
May 18, 2019, 10:49am
#8
Edit Screen Controller:
package de.nexloy.crm.vorgangsverwaltung.web.vorgang;
import com.haulmont.bali.util.ParamsMap;
import com.haulmont.cuba.core.entity.Entity;
import com.haulmont.cuba.core.global.Metadata;
import com.haulmont.cuba.core.global.PersistenceHelper;
import com.haulmont.cuba.gui.WindowManager;
import com.haulmont.cuba.gui.components.*;
import com.haulmont.cuba.gui.components.Button;
import com.haulmont.cuba.gui.components.Component;
import com.haulmont.cuba.gui.components.Label;
import com.haulmont.cuba.gui.components.TextField;
import com.haulmont.cuba.gui.components.Window;
import com.haulmont.cuba.gui.components.actions.CreateAction;
import com.haulmont.cuba.gui.components.actions.EditAction;
import com.haulmont.cuba.gui.data.CollectionDatasource;
import com.haulmont.cuba.gui.data.Datasource;
import com.haulmont.cuba.gui.data.GroupDatasource;
import com.haulmont.cuba.gui.model.DataContext;
import com.haulmont.cuba.gui.xml.layout.ComponentsFactory;
import com.haulmont.cuba.security.global.UserSession;
import com.haulmont.reports.entity.Report;
import com.haulmont.reports.gui.ReportGuiManager;
import de.nexloy.crm.vorgangsverwaltung.entity.*;
import javax.annotation.Nullable;
import javax.inject.Inject;
import javax.inject.Named;
import java.util.*;
import java.util.List;
/**
* @author jwoehlke
*/
public class VorgangEdit extends AbstractEditor<Vorgang> {
@Inject
private ComponentsFactory componentsFactory;
@Inject
private UserSession userSession;
@Inject
private Metadata metadata;
@Inject
private ReportGuiManager reportGuiManager;
@Inject
private DataContext dataContext;
// --------------------- Datasources: ------------------------------
@Inject
private CollectionDatasource<VorgangHistorie, Long> vorgangHistoriesDs;
@Inject
private CollectionDatasource<KndKrtn, Long> kndKrtnsDs;
@Inject
private Datasource<Vorgang> vorgangDs;
@Inject
private CollectionDatasource<Vorgangskategorie, Long> vorgangskategoriesDs;
@Inject
private GroupDatasource<Vorgang,Long> kndVorgangsDs;
// --------------------- GUI-Components: ------------------------------
@Inject
private TextField customerCardId;
@Inject
private TextField tfKontaktperson;
@Inject
private LookupField lfStatus;
@Inject
private LookupField lfProcessGroup;
@Inject
private DateField dfDeadline;
@Inject
private PickerField customerId;
@Inject
private Button btnSaveAndNew;
@Inject
private Button btnSave;
@Inject
private TabSheet tabSheet;
// Beschreibung:
@Named("gbDesc")
private GroupBoxLayout gbDesc;
@Inject
private RichTextArea rtfDesc; // beschreibung
// Data Grid - VorgangsHistorie:
@Named("GbHistory")
private GroupBoxLayout gbHistory;
@Inject
private DataGrid<VorgangHistorie> vorgangshistorieDataGrid;
@Named("vorgangshistorieDataGrid.edit")
private EditAction vorgangshistorieDataGridEditAction;
@Named("vorgangshistorieDataGrid.create")
private CreateAction vorgangshistorieDataGridCreateAction;
@Override
public void init(Map<String, Object> params) {
// Validator fuer Vorgangs-Status
lfStatus.addValidator(value -> {
Status status = (Status) value;
if(status.equals(Status.inArbeit) && dfDeadline.getValue() == null){
throw new ValidationException(this.getMessage("validation.error.deadlineNotSet"));
}
});
// dynamischer Filter fuer Vorgangskategorien:
lfProcessGroup.addValueChangeListener(e -> {
HasValue.ValueChangeEvent<VorgangGruppe> event = (HasValue.ValueChangeEvent<VorgangGruppe>)e;
if (event.getValue() != null) {
vorgangskategoriesDs.refresh();
List<Vorgangskategorie> allCategories = new ArrayList<>(vorgangskategoriesDs.getItems());
vorgangskategoriesDs.clear(); // ??
allCategories.stream().filter(e2 -> e2.getVorgangGruppe().equals(event.getValue())).forEach(vorgangskategoriesDs::addItem);
}else{
vorgangskategoriesDs.refresh();
}
});
// Automatisches Laden des Kunden anhand der Kartennummer:
customerCardId.addValueChangeListener(event -> {
HasValue.ValueChangeEvent<Long> e = (HasValue.ValueChangeEvent<Long>)event;
// update collection to filter by input:
kndKrtnsDs.refresh();
// get actual item by input - should be available after refresh:
KndKrtn kndKrte = kndKrtnsDs.getItem(e.getValue());
if(kndKrte != null && kndKrte.getKndNr() != null) {
getItem().setKndNr(kndKrte.getKndNr());
}else{
this.showNotification("Failed to set customer value!", NotificationType.TRAY);
}
});
// Standard Kontaktperson:
customerId.addValueChangeListener(event -> {
HasValue.ValueChangeEvent<KndDtn> e = (HasValue.ValueChangeEvent<KndDtn>) event;
if(e.getValue() != null && e.getValue() instanceof KndDtn && tfKontaktperson!=null && ( tfKontaktperson.getRawValue() == null || tfKontaktperson.getRawValue().isEmpty() )){
//set default kontaktperson
tfKontaktperson.setValue(this.getMessage("defaultKontaktperson"));
}
if(e.getValue() != null && e.getValue() instanceof KndDtn) {
updateKndVorgengeTabVisibility((KndDtn) e.getValue());
}
});
// Layout fuer Vorgangshistorie:
vorgangshistorieDataGrid.setDetailsGenerator(new DataGrid.DetailsGenerator<VorgangHistorie>() {
@Nullable
@Override
public Component getDetails(VorgangHistorie entity) {
VBoxLayout mainLayout = componentsFactory.createComponent(VBoxLayout.class);
mainLayout.setWidth("100%");
mainLayout.setMargin(true);
mainLayout.setSpacing(true);
Label contentLabel = componentsFactory.createComponent(Label.class);
contentLabel.setHtmlEnabled(true);
contentLabel.setWidth("98%");
if(entity == null || entity.getText() == null){
contentLabel.setValue("-");
}else{
contentLabel.setValue(entity.getText());
}
mainLayout.add(contentLabel);
mainLayout.expand(contentLabel);
return mainLayout;
}
});
/* close Button für Vorgangshistorie Ansicht:
DataGrid.Column column = vorgangshistorieDataGrid.addGeneratedColumn("closeButton",
new DataGrid.ColumnGenerator<VorgangHistorie, Component>() {
int i = 0;
@Override
public Component getValue(DataGrid.ColumnGeneratorEvent<VorgangHistorie> event){
Button closeButton = componentsFactory.createComponent(Button.class);
closeButton.setIcon("icons/remove.png");
closeButton.setCaption("");
closeButton.setId("closeButton "+i);
closeButton.setAction(new BaseAction("closeDetailsId"){
@Override
public void actionPerform(Component component){
hideVorgangHistorieItemDetails(event.getItem());
}
});
return closeButton;
}
@Override
public Class<Component> getType() {
return Component.class;
}
}
);
column.setRenderer(new WebComponentRenderer());
*/
// Vorgangshistorie: toggle details on click
vorgangshistorieDataGrid.addItemClickListener(event -> {
if(vorgangshistorieDataGrid.isDetailsVisible(event.getItem())) {
vorgangshistorieDataGrid.setDetailsVisible(event.getItem(), false);
}else{
vorgangshistorieDataGrid.setDetailsVisible(event.getItem(), true);
}
});
// Vorgangshistorie: Update Table after insert/update
vorgangshistorieDataGridEditAction.setAfterCommitHandler(entity ->
refreshAndShowDetailsInHistory()
);
vorgangshistorieDataGridCreateAction.setAfterCommitHandler(entity ->
refreshAndShowDetailsInHistory()
);
// on create action: set vorgang id in vorgang historie:
vorgangshistorieDataGridCreateAction.setInitialValuesSupplier(
()-> ParamsMap.of("vorgang", vorgangDs.getItem())
);
dataContext.addPostCommitListener(event -> {
Entity committedEntity = event.getCommittedInstances().stream()
.filter(entity -> entity.equals(getEditedEntity()))
.findFirst()
.get();
Long id = ((Vorgang) committedEntity).getId();
showMessageDialog("Test", "ID:" + id, MessageType.CONFIRMATION);
});
// finish init:
super.init(params);
}
/* Vorgangshistorie: for close button!
private void hideVorgangHistorieItemDetails(VorgangHistorie entity){
vorgangshistorieDataGrid.setDetailsVisible(entity, false);
}
*/
@Override
protected void postInit() {
if (PersistenceHelper.isNew(getItem())) {
btnSaveAndNew.setVisible(true);
btnSave.setVisible(false);
}else{
btnSaveAndNew.setVisible(false);
btnSave.setVisible(true);
}
if(getItem() != null){
this.updateKndVorgengeTabVisibility(getItem().getKndNr());
}
refreshAndShowDetailsInHistory();
}
private void refreshAndShowDetailsInHistory(){
vorgangHistoriesDs.refresh();
// show details for all items in history:
for (VorgangHistorie item : vorgangHistoriesDs.getItems()) {
vorgangshistorieDataGrid.setDetailsVisible(item, true);
}
}
@Override
protected void initNewItem(Vorgang item) {
//default parameter:
item.setKontaktrichtung(Kontaktrichtung.fromId("Inbound"));
item.setStatus(Status.fromId("Offen"));
item.setExportSperre(JaNein.Nein);
item.setRueckmeldungErwuenscht(JaNein.Nein);
// no history creation allowed
this.gbHistory.setVisible(false);
this.gbDesc.setVisible(true);
}
@Override
protected boolean preCommit() {
// changed entity
if(vorgangDs.isModified()) {
Vorgang v = this.getItem();
if(v.getStatus().equals(Status.inArbeit) && v.getTerminAm() == null){
return false;
}else if(v.getStatus().equals(Status.offen) && v.getTerminAm() != null){
v.setTerminAm(null);
this.showNotification(this.messages.getMessage(getClass(),"validation.info.deadlineNull"), NotificationType.TRAY);
}
if(!v.getVorgangskategorie().getVorgangGruppe().equals(v.getVorgangGruppe())){
this.showNotification(this.messages.getMessage(getClass(),"validation.error.wrongProcessGroup"),NotificationType.ERROR);
return false;
}
if(v.getAngelegtAm() == null){
v.setAngelegtAm(new Date());
}
if(v.getAngelegtVon() == null || v.getAngelegtVon().isEmpty()){
v.setAngelegtVon(userSession.getUser().getLoginLowerCase());
}
//set changed date - always!:
v.setGeaendertAm(new Date());
v.setGeaendertVon(userSession.getUser().getLoginLowerCase());
// is not newly created:
if(v.getId()!=null && v.getId() > 0) {
// Log changes - only if not updated before manually!
// get max Id for history Item:
long maxId = -1;
for(VorgangHistorie veTmp1 : vorgangHistoriesDs.getItems()){
if(veTmp1.getVorgang().getId().compareTo(v.getId()) == 0){
maxId = veTmp1.getId();
}
}
// check last entry:
boolean resultVorgangHistoryEntryExists = false;
Date dTmpXMinBefore = new Date();
dTmpXMinBefore.setTime(System.currentTimeMillis()-(30*60*1000)); // -30 Min
VorgangHistorie veTmp2 = vorgangHistoriesDs.getItem(maxId);
if (
veTmp2.getCreatedBy().equalsIgnoreCase(userSession.getUser().getLoginLowerCase())
&&
!veTmp2.getText().isEmpty()
&&
veTmp2.getCreateTs().before(dTmpXMinBefore)
){
resultVorgangHistoryEntryExists = true;
}
if(!vorgangHistoriesDs.isModified() && !resultVorgangHistoryEntryExists) {
VorgangHistorie vorgangHistorieNewItem = metadata.create(VorgangHistorie.class);
vorgangHistorieNewItem.setVorgang(v);
vorgangHistorieNewItem.setText(this.messages.getMessage(getClass(), "historyCommitLogMessage"));
vorgangHistoriesDs.addItem(vorgangHistorieNewItem);
}
}else{
// Write Description as History Item
VorgangHistorie vorgangHistorieNewItem = metadata.create(VorgangHistorie.class);
vorgangHistorieNewItem.setVorgang(v);
if(rtfDesc.getValue()!=null && !rtfDesc.getValue().isEmpty()) {
vorgangHistorieNewItem.setText(rtfDesc.getValue());
}else{
vorgangHistorieNewItem.setText(this.messages.getMessage(getClass(), "historyCommitLogMessage"));
}
vorgangHistoriesDs.addItem(vorgangHistorieNewItem);
}
}
return true;
}
@Override
protected boolean postCommit(boolean committed, boolean close) {
if(committed && vorgangHistoriesDs.isModified()) {
vorgangHistoriesDs.commit();
}
return super.postCommit(committed, close);
}
private void updateKndVorgengeTabVisibility(KndDtn knd){
TabSheet.Tab t = null;
Iterator <TabSheet.Tab> iterator = tabSheet.getTabs().iterator();
while(iterator.hasNext()){
t = iterator.next();
if(t.getName().contains("kndVorgaengeTab")){
break;
}
}
if(t != null) {
if (knd != null && knd instanceof KndDtn) {
t.setVisible(true);
kndVorgangsDs.refresh();
} else {
t.setVisible(false);
}
}else{
this.showNotification("Error: Tab not found!");
}
}
public void onExportButtonClick() {
List<Report> reports = reportGuiManager.getAvailableReports(getId(),userSession.getUser(),getItem().getMetaClass());
if(reports.size()>0) {
for (Report r : reports) {
if(r.getName().contains("Vorgangsexport")) {
Map<String,Object> reportParams = new HashMap<>();
reportParams.put("Vorgang",this.getItem());
reportParams.put("Vorgangshistorie",vorgangHistoriesDs.getItems());
reportGuiManager.printReport(r,reportParams,"DEFAULT","Vorgangsexport");
}
}
}else{
this.showNotification("Error: No report found!");
}
}
public void onBtnCancelClick() {
this.close(Window.CLOSE_ACTION_ID);
}
public void onBtnSaveClick() {
this.commit();
}
public void onBtnSaveAndCloseClick() {
this.commitAndClose();
}
public void onBtnSaveAndNewClick() {
this.commitAndClose();
this.openEditor(new Vorgang(), WindowManager.OpenType.NEW_TAB);
}
}
krivopustov
(Konstantin Krivopustov)
May 22, 2019, 8:51am
#9
Your screen is based on the legacy API, so there is no DataContext
in it.
Also, better use BaseLongIdEntity
as a base class for your entity and annotate it with @IdSequence , specifying the name of your sequence. Then the id will be assigned right after creation of the entity in memory and all framework mechanisms will work as expected.
jw90
May 23, 2019, 6:03am
#10
Thank you! I will try another controller class then.
About the @IdSequence I have an open request concerning a problem with that.
Hi there, I’m using an oracle database as an additional data source. When I’m using @IdSequence on an Entity, then a new IdSequence is created in the main database, but the sequence in oracle database is not used. Furthermore there are sequences...
Kind regards,
J
jw90
May 25, 2019, 10:08am
#11
Hi again,
I rewrote everything, but now I’m getting an error, I don’t understand:
ClassCastException: de.nexloy.crm.vorgangsverwaltung.web.vorgang.VorgangEdit cannot be cast to com.haulmont.cuba.gui.screen.compatibility.LegacyFrame
I hope you can help me again.
Thank you very much for your help.
Entity:
/*
* Copyright Nexloy 2018
*/
package de.nexloy.crm.vorgangsverwaltung.entity;
import com.haulmont.chile.core.annotations.NamePattern;
import com.haulmont.cuba.core.entity.BaseIdentityIdEntity;
import com.haulmont.cuba.core.entity.annotation.IdSequence;
import com.haulmont.cuba.core.global.DesignSupport;
import javax.persistence.*;
import java.util.Date;
/**
* @author jwoehlke
*/
@NamePattern("%s %s|id,bezug")
@DesignSupport("{'imported':true}")
@Table(name = "VORGANG")
@Entity(name = "vorgangsverwaltung$Vorgang")
@IdSequence(name = "VORGANG_ID_SEQ",cached = true)
public class Vorgang extends BaseIdentityIdEntity
{
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "KND_NR")
protected KndDtn kndNr;
@Column(name = "KONTAKTPERSON", nullable = false, length = 100)
protected String kontaktperson;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "FIL_NR")
protected Fil filNr;
@Column(name = "KONTAKTART", nullable = false)
protected String kontaktart;
@Column(name = "KONTAKTRICHTUNG", nullable = false)
protected String kontaktrichtung;
@ManyToOne(fetch = FetchType.LAZY, optional = false)
@JoinColumn(name = "VORGANGSKATEGORIE_ID")
protected Vorgangskategorie vorgangskategorie;
@Column(name = "BEZUG", length = 500)
protected String bezug;
@Column(name = "STATUS", nullable = false)
protected String status;
@Column(name = "ANGELEGT_VON", nullable = false, length = 100)
protected String angelegtVon;
@Temporal(TemporalType.DATE)
@Column(name = "ANGELEGT_AM", nullable = false)
protected Date angelegtAm;
@Column(name = "GEAENDERT_VON", nullable = false, length = 100)
protected String geaendertVon;
@Temporal(TemporalType.DATE)
@Column(name = "GEAENDERT_AM", nullable = false)
protected Date geaendertAm;
@Temporal(TemporalType.DATE)
@Column(name = "TERMIN_AM")
protected Date terminAm;
@Column(name = "KONTAKTINFO", length = 100)
protected String kontaktinfo;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "KONTAKTGRUPPE_ID")
protected VorgangKontaktgruppe kontaktgruppe;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "MARKE_ID")
protected VorgangMarke marke;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "ARTIKEL_NR")
protected Artkl artikelNr;
@Column(name = "ARTIKEL_INFO", length = 100)
protected String artikelInfo;
@Column(name = "ANLIEGEN", length = 4000)
protected String anliegen;
@Column(name = "RUECKMELDUNG_ERWUENSCHT")
protected Integer rueckmeldungErwuenscht;
@Column(name = "ARTIKELEINGABE")
protected Long artikeleingabe;
@Column(name = "EXPORT_SPERRE")
protected Integer exportSperre;
@Temporal(TemporalType.DATE)
@Column(name = "EXPORT_DATUM")
protected Date exportDatum;
@Column(name = "GEAENDERT_VON_ALLE", length = 100)
protected String geaendertVonAlle;
@Temporal(TemporalType.DATE)
@Column(name = "GEAENDERT_AM_ALLE")
protected Date geaendertAmAlle;
@ManyToOne(fetch = FetchType.LAZY)
@JoinColumn(name = "VORGANG_GRUPPE_ID")
protected VorgangGruppe vorgangGruppe;
public VorgangGruppe getVorgangGruppe() {
return vorgangGruppe;
}
public void setVorgangGruppe(VorgangGruppe vorgangGruppe) {
this.vorgangGruppe = vorgangGruppe;
}
public JaNein getExportSperre() {
return exportSperre == null ? null : JaNein.fromId(exportSperre);
}
public void setExportSperre(JaNein exportSperre) {
this.exportSperre = exportSperre == null ? null : exportSperre.getId();
}
public JaNein getRueckmeldungErwuenscht() {
return rueckmeldungErwuenscht == null ? null : JaNein.fromId(rueckmeldungErwuenscht);
}
public void setRueckmeldungErwuenscht(JaNein rueckmeldungErwuenscht) {
this.rueckmeldungErwuenscht = rueckmeldungErwuenscht == null ? null : rueckmeldungErwuenscht.getId();
}
public Status getStatus() {
return status == null ? null : Status.fromId(status);
}
public void setStatus(Status status) {
this.status = status == null ? null : status.getId();
}
public Kontaktrichtung getKontaktrichtung() {
return kontaktrichtung == null ? null : Kontaktrichtung.fromId(kontaktrichtung);
}
public void setKontaktrichtung(Kontaktrichtung kontaktrichtung) {
this.kontaktrichtung = kontaktrichtung == null ? null : kontaktrichtung.getId();
}
public Kontaktart getKontaktart() {
return kontaktart == null ? null : Kontaktart.fromId(kontaktart);
}
public void setKontaktart(Kontaktart kontaktart) {
this.kontaktart = kontaktart == null ? null : kontaktart.getId();
}
public void setKndNr(KndDtn kndNr) {
this.kndNr = kndNr;
}
public KndDtn getKndNr() {
return kndNr;
}
public void setKontaktperson(String kontaktperson) {
this.kontaktperson = kontaktperson;
}
public String getKontaktperson() {
return kontaktperson;
}
public void setFilNr(Fil filNr) {
this.filNr = filNr;
}
public Fil getFilNr() {
return filNr;
}
public void setVorgangskategorie(Vorgangskategorie vorgangskategorie) {
this.vorgangskategorie = vorgangskategorie;
}
public Vorgangskategorie getVorgangskategorie() {
return vorgangskategorie;
}
public void setBezug(String bezug) {
this.bezug = bezug;
}
public String getBezug() {
return bezug;
}
public void setAngelegtVon(String angelegtVon) {
this.angelegtVon = angelegtVon;
}
public String getAngelegtVon() {
return angelegtVon;
}
public void setAngelegtAm(Date angelegtAm) {
this.angelegtAm = angelegtAm;
}
public Date getAngelegtAm() {
return angelegtAm;
}
public void setGeaendertVon(String geaendertVon) {
this.geaendertVon = geaendertVon;
}
public String getGeaendertVon() {
return geaendertVon;
}
public void setGeaendertAm(Date geaendertAm) {
this.geaendertAm = geaendertAm;
}
public Date getGeaendertAm() {
return geaendertAm;
}
public void setTerminAm(Date terminAm) {
this.terminAm = terminAm;
}
public Date getTerminAm() {
return terminAm;
}
public void setKontaktinfo(String kontaktinfo) {
this.kontaktinfo = kontaktinfo;
}
public String getKontaktinfo() {
return kontaktinfo;
}
public void setKontaktgruppe(VorgangKontaktgruppe kontaktgruppe) {
this.kontaktgruppe = kontaktgruppe;
}
public VorgangKontaktgruppe getKontaktgruppe() {
return kontaktgruppe;
}
public void setMarke(VorgangMarke marke) {
this.marke = marke;
}
public VorgangMarke getMarke() {
return marke;
}
public void setArtikelNr(Artkl artikelNr) {
this.artikelNr = artikelNr;
}
public Artkl getArtikelNr() {
return artikelNr;
}
public void setArtikelInfo(String artikelInfo) {
this.artikelInfo = artikelInfo;
}
public String getArtikelInfo() {
return artikelInfo;
}
public void setAnliegen(String anliegen) {
this.anliegen = anliegen;
}
public String getAnliegen() {
return anliegen;
}
public void setArtikeleingabe(Long artikeleingabe) {
this.artikeleingabe = artikeleingabe;
}
public Long getArtikeleingabe() {
return artikeleingabe;
}
public void setExportDatum(Date exportDatum) {
this.exportDatum = exportDatum;
}
public Date getExportDatum() {
return exportDatum;
}
public void setGeaendertVonAlle(String geaendertVonAlle) {
this.geaendertVonAlle = geaendertVonAlle;
}
public String getGeaendertVonAlle() {
return geaendertVonAlle;
}
public void setGeaendertAmAlle(Date geaendertAmAlle) {
this.geaendertAmAlle = geaendertAmAlle;
}
public Date getGeaendertAmAlle() {
return geaendertAmAlle;
}
}
jw90
May 25, 2019, 10:10am
#12
Screen Descriptor:
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<window xmlns="http://schemas.haulmont.com/cuba/screen/window.xsd" caption="msg://editorCaption" focusComponent="form"
messagesPack="de.nexloy.crm.vorgangsverwaltung.web.vorgang">
<data>
<instance id="vorgangDc"
class="de.nexloy.crm.vorgangsverwaltung.entity.Vorgang"
view="_local">
<instance id="kndNrDc" property="kndNr"/>
<instance id="filNrDc" property="filNr"/>
<instance id="vorgangskategorieDc" property="vorgangskategorie"/>
<instance id="kontaktgruppeDc" property="kontaktgruppe"/>
<instance id="markeDc" property="marke"/>
<instance id="artikelNrDc" property="artikelNr"/>
<instance id="vorgangGruppeDc" property="vorgangGruppe"/>
</instance>
<collection id="artikelNrsDc"
class="de.nexloy.crm.vorgangsverwaltung.entity.Artkl" view="_minimal">
<loader cacheable="false">
<query><![CDATA[select e from vorgangsverwaltung$Artkl e]]></query>
</loader>
</collection>
<collection id="vorgangGruppesDc"
class="de.nexloy.crm.vorgangsverwaltung.entity.VorgangGruppe" view="_minimal">
<loader cacheable="true">
<query><![CDATA[select e from vorgangsverwaltung$VorgangGruppe e where e.istAktiv = 1]]></query>
</loader>
</collection>
<collection id="vorgangskategoriesDc"
class="de.nexloy.crm.vorgangsverwaltung.entity.Vorgangskategorie"
view="vorgangskategorie-view">
<loader cacheable="true">
<query><![CDATA[select e from vorgangsverwaltung$Vorgangskategorie e where e.ist_aktiv = 1]]></query>
</loader>
</collection>
<collection id="vorgangMarkesDc"
class="de.nexloy.crm.vorgangsverwaltung.entity.VorgangMarke" view="_minimal">
<loader cacheable="true">
<query><![CDATA[select e from vorgangsverwaltung$VorgangMarke e]]></query>
</loader>
</collection>
<collection id="vorgangKontaktgruppesDc"
class="de.nexloy.crm.vorgangsverwaltung.entity.VorgangKontaktgruppe" view="_minimal">
<loader cacheable="true">
<query><![CDATA[select e from vorgangsverwaltung$VorgangKontaktgruppe e]]></query>
</loader>
</collection>
<collection id="vorgangHistoriesDc" class="de.nexloy.crm.vorgangsverwaltung.entity.VorgangHistorie"
view="vorgangHistorie-full-view">
<loader id="vorgangHistoriesDl" cacheable="false">
<query>
<![CDATA[select e from vorgangsverwaltung$VorgangHistorie e
where :vorgangId = e.vorgang.id
order by e.createTs desc]]>
</query>
</loader>
</collection>
<collection id="kndKrtnsDc"
class="de.nexloy.crm.vorgangsverwaltung.entity.KndKrtn" view="kndKrtn-view">
<loader cacheable="false">
<query><![CDATA[select e from vorgangsverwaltung$KndKrtn e where e.id = :component$customerCardId]]></query>
</loader>
</collection>
<collection id="filsDc" class="de.nexloy.crm.vorgangsverwaltung.entity.Fil"
view="Fil-screen-view">
<loader cacheable="true">
<query><![CDATA[select e from vorgangsverwaltung$Fil e where e.filstatus.id = 0]]></query>
</loader>
</collection>
<collection id="artklSearchDc"
class="de.nexloy.crm.vorgangsverwaltung.entity.Artkl" view="Artkl-screen-view">
<loader id="artklSearchDl" cacheable="false">
<query><![CDATA[select e from vorgangsverwaltung$Artkl e where e.id like CONCAT(:custom$searchString,'%')]]></query>
</loader>
</collection>
<collection id="kndVorgangsDc" class="de.nexloy.crm.vorgangsverwaltung.entity.Vorgang"
view="Vorgang-screen-view">
<loader id="kndVorgangsDl">
<query><![CDATA[select e from vorgangsverwaltung$Vorgang e
where :vorgangKndNr = e.kndNr.id
order by e.id desc]]></query>
</loader>
</collection>
</data>
<layout spacing="true">
<form id="form" dataContainer="vorgangDc">
<scrollBox height="100%" margin="true">
<buttonsPanel height="50px" responsive="true">
<button id="btnSave" caption="msg://speichern" invoke="onBtnSaveClick" stylename="primary"/>
<button id="btnSaveAndClose" caption="msg://speichern_und_schliessen" invoke="onBtnSaveAndCloseClick"
stylename="primary"/>
<button id="btnSaveAndNew" caption="msg://speichern_und_neu" invoke="onBtnSaveAndNewClick"
stylename="friendly"/>
<button id="btnCancel" invoke="onBtnCancelClick" caption="msg://cancel" stylename="danger"/>
</buttonsPanel>
<hbox height="50px" margin="true,false,true,false" responsive="true" visible="false">
<frame height="35px" width="AUTO" align="MIDDLE_LEFT" screen="editWindowActions"/>
</hbox>
<tabSheet id="tabSheet">
<tab id="tab-general" caption="msg://allgemein" margin="true" spacing="true">
<vbox>
<flowBox>
<groupBox id="gbVorgang" caption="msg://vorgang" height="540px" outerMargin="true"
settingsEnabled="false" width="AUTO">
<textField id="id" caption="msg://vorgang_id" dataContainer="vorgangDc" datatype="long"
editable="false" property="id"/>
<textField id="tfKontaktperson" caption="msg://kontaktperson" dataContainer="vorgangDc"
datatype="string" property="kontaktperson" width="350px"/>
<textField id="tfContactInfo" caption="msg://kontaktinfo" dataContainer="vorgangDc"
datatype="string" property="kontaktinfo" width="350px"/>
<lookupPickerField id="lpfFilNr" caption="msg://filNr" dataContainer="vorgangDc"
optionsContainer="filsDc" property="filNr" width="350px">
<actions>
<action id="lookup"/>
</actions>
</lookupPickerField>
<lookupField id="lfContactType" caption="msg://kontaktart" dataContainer="vorgangDc"
optionsEnum="de.nexloy.crm.vorgangsverwaltung.entity.Kontaktart"
property="kontaktart" required="true" width="350px"/>
<optionsGroup id="ogContactDirection" caption="msg://kontaktrichtung"
dataContainer="vorgangDc"
optionsEnum="de.nexloy.crm.vorgangsverwaltung.entity.Kontaktrichtung"
orientation="horizontal" property="kontaktrichtung" visible="false"/>
<lookupField id="lfProcessGroup" caption="msg://vorgangsgruppe" dataContainer="vorgangDc"
optionsContainer="vorgangGruppesDc" property="vorgangGruppe" width="350px"
required="true"/>
<lookupField id="lfProcessCategory" caption="msg://vorgangskategorie"
dataContainer="vorgangDc" optionsContainer="vorgangskategoriesDc"
property="vorgangskategorie" width="350px" required="true"/>
<textField id="tfSubject" dataContainer="vorgangDc" property="bezug" width="350px"
caption="msg://bezug" datatype="string"/>
<lookupField id="lfStatus" caption="msg://status" dataContainer="vorgangDc"
optionsEnum="de.nexloy.crm.vorgangsverwaltung.entity.Status"
property="status" width="350px"/>
<dateField id="dfDeadline" caption="msg://terminAm" dataContainer="vorgangDc"
dateFormat="msg://dateFormat" property="terminAm" width="350px"/>
</groupBox>
<groupBox id="gbDesc" caption="msg://beschreibung" height="540px" outerMargin="true"
settingsEnabled="false" visible="false" width="750px">
<richTextArea id="rtfDesc" height="100%" width="100%"/>
</groupBox>
<groupBox id="gbKunde" caption="msg://kunde" height="540px" outerMargin="true"
settingsEnabled="false" width="AUTO">
<vbox spacing="true">
<textField id="customerCardId" caption="msg://customerCardId" datatype="long"
width="350px"/>
<pickerField id="customerId" caption="msg://kndNr" dataContainer="vorgangDc"
property="kndNr" width="350px">
<actions>
<action id="lookup"/>
<action id="clear"/>
<action id="open"/>
</actions>
</pickerField>
</vbox>
</groupBox>
<groupBox id="GbHistory" height="540px" width="750px" outerMargin="true" settingsEnabled="false">
<dataGrid id="vorgangshistorieDataGrid" columnsCollapsingAllowed="false"
dataContainer="vorgangHistoriesDc" height="100%" width="100%">
<actions>
<action id="create" caption="msg://neu"/>
<action id="refresh"/>
<action id="edit" caption="msg://bearbeiten"/>
<action id="refresh" caption="msg://refresh"/>
</actions>
<columns>
<column id="createTs" caption="msg://createTs" editable="false"
property="createTs"/>
<column id="createdBy" caption="msg://createdBy" editable="false"
property="createdBy"/>
</columns>
<buttonsPanel>
<button id="createDataGridBtn" action="vorgangshistorieDataGrid.create"
caption="msg://neu" icon="icons/plus-btn.png"/>
<button id="saveDataGridBtn" action="vorgangshistorieDataGrid.edit"/>
<button id="refreshDataGridBtn" action="vorgangshistorieDataGrid.refresh"/>
</buttonsPanel>
</dataGrid>
</groupBox>
</flowBox>
</vbox>
</tab>
<tab id="markenTab" caption="msg://eigenmarke" margin="true" spacing="true">
<searchPickerField id="spArticleNr" caption="msg://artikel" dataContainer="vorgangDc" optionsContainer="artklSearchDc" captionProperty="artikelNr"
property="artikelNr" width="350px" minSearchStringLength="1">
<actions>
<action id="lookup" type="picker_lookup"/>
<action id="open" type="picker_open"/>
</actions>
</searchPickerField>
<textField caption="msg://artikelInfo" dataContainer="vorgangDc" property="artikelInfo" width="350px"/>
<lookupPickerField id="lpBrand" caption="msg://marke" dataContainer="vorgangDc"
optionsContainer="vorgangMarkesDc" property="marke" width="350px">
<actions>
<action id="lookup" type="picker_lookup"/>
<action id="open" type="picker_open"/>
</actions>
</lookupPickerField>
<lookupField caption="msg://kontaktgruppe" dataContainer="vorgangDc"
optionsContainer="vorgangKontaktgruppesDc" property="kontaktgruppe" width="350px"/>
<textArea caption="msg://anliegen" dataContainer="vorgangDc" maxLength="4000" property="anliegen"
width="350px"/>
<optionsGroup caption="msg://rueckmeldung" dataContainer="vorgangDc"
optionsEnum="de.nexloy.crm.vorgangsverwaltung.entity.JaNein" orientation="horizontal"
property="rueckmeldungErwuenscht" width="350px" required="true"/>
<optionsGroup caption="msg://exportSperre" dataContainer="vorgangDc"
optionsEnum="de.nexloy.crm.vorgangsverwaltung.entity.JaNein" orientation="horizontal"
property="exportSperre" width="350px" required="true"/>
<dateField id="dfExportDatum" caption="msg://exportDatum" dataContainer="vorgangDc" editable="false"
enable="false" property="exportDatum"/>
</tab>
<tab id="kndVorgaengeTab" caption="msg://kndVorgaenge" margin="true,false,false,false" spacing="true"
visible="false">
<groupTable id="groupTableKndVorgaenge" height="100%" width="100%" dataContainer="kndVorgangsDc">
<actions>
<action id="edit" openType="NEW_TAB"/>
</actions>
<columns>
<column id="id" caption="msg://vorgang_id"/>
<column id="kontaktart" caption="msg://kontaktart"/>
<column id="kontaktgruppe" caption="msg://kontaktgruppe"/>
<column id="vorgangskategorie" caption="msg://vorgangskategorie"/>
<column id="filNr" caption="msg://filiale"/>
<column id="bezug" caption="msg://bezug"/>
<column id="status" caption="msg://status"/>
<column id="angelegtVon" caption="msg://angelegtVon"/>
<column id="angelegtAm" caption="msg://angelegtAm"/>
<column id="geaendertVon" caption="msg://geaendertVon"/>
<column id="geaendertAm" caption="msg://geaendertAm"/>
</columns>
<rows/>
<buttonsPanel>
<button caption="msg://bearbeiten" action="groupTableKndVorgaenge.edit"/>
</buttonsPanel>
</groupTable>
</tab>
<tab id="exportTab" caption="msg://Export" margin="true" spacing="true">
<groupBox id="gbVorgangsexport" caption="msg://Vorgangsexport" outerMargin="true" spacing="true">
<button id="exportButton" caption="msg://Export" invoke="onExportButtonClick" icon="PRINT"/>
</groupBox>
</tab>
</tabSheet>
</scrollBox>
</form>
</layout>
</window>
jw90
May 25, 2019, 10:10am
#13
Controller:
package de.nexloy.crm.vorgangsverwaltung.web.vorgang;
import com.haulmont.bali.util.ParamsMap;
import com.haulmont.cuba.core.entity.Entity;
import com.haulmont.cuba.core.entity.IdProxy;
import com.haulmont.cuba.core.global.Messages;
import com.haulmont.cuba.core.global.Metadata;
import com.haulmont.cuba.core.global.PersistenceHelper;
import com.haulmont.cuba.gui.Dialogs;
import com.haulmont.cuba.gui.Notifications;
import com.haulmont.cuba.gui.ScreenBuilders;
import com.haulmont.cuba.gui.UiComponents;
import com.haulmont.cuba.gui.components.*;
import com.haulmont.cuba.gui.components.Button;
import com.haulmont.cuba.gui.components.Component;
import com.haulmont.cuba.gui.components.Label;
import com.haulmont.cuba.gui.components.TextField;
import com.haulmont.cuba.gui.components.actions.CreateAction;
import com.haulmont.cuba.gui.components.actions.EditAction;
import com.haulmont.cuba.gui.data.CollectionDatasource;
import com.haulmont.cuba.gui.data.Datasource;
import com.haulmont.cuba.gui.data.GroupDatasource;
import com.haulmont.cuba.gui.model.CollectionLoader;
import com.haulmont.cuba.gui.model.DataContext;
import com.haulmont.cuba.gui.model.InstanceContainer;
import com.haulmont.cuba.gui.model.InstanceLoader;
import com.haulmont.cuba.gui.screen.*;
import com.haulmont.cuba.security.global.UserSession;
import com.haulmont.reports.entity.Report;
import com.haulmont.reports.gui.ReportGuiManager;
import de.nexloy.crm.vorgangsverwaltung.entity.*;
import javax.annotation.Nullable;
import javax.inject.Inject;
import javax.inject.Named;
import java.util.*;
import java.util.List;
/**
* @author jwoehlke
*/
@UiController("vorgangsverwaltung$Vorgang.edit")
@UiDescriptor("vorgang-edit.xml")
@EditedEntityContainer("vorgangDc")
@LoadDataBeforeShow
public class VorgangEdit extends StandardEditor<Vorgang>{
@Inject
private UiComponents uiComponents;
@Inject
private UserSession userSession;
@Inject
private Metadata metadata;
@Inject
private ReportGuiManager reportGuiManager;
@Inject
private Messages messages;
@Inject
private Notifications notifications;
@Inject
private Dialogs dialogs;
@Inject
private ScreenBuilders screenBuilders;
// --------------------- DataContainer & DataLoader: ------------------------------
@Inject
private CollectionDatasource<VorgangHistorie, Long> vorgangHistoriesDc;
@Inject
private CollectionLoader<VorgangHistorie> vorgangHistoriesDl;
@Inject
private CollectionDatasource<KndKrtn, Long> kndKrtnsDc;
@Inject
private Datasource<Vorgang> vorgangDc;
@Inject
private InstanceLoader<Vorgang> vorgangDl;
@Inject
private CollectionDatasource<Vorgangskategorie, Long> vorgangskategoriesDc;
@Inject
private GroupDatasource<Vorgang, IdProxy<Long>> kndVorgangsDc;
@Inject
private CollectionLoader<Vorgang> kndVorgangsDl;
@Inject
private CollectionDatasource<Artkl,Long> artklSearchDc;
// --------------------- GUI-Components: ------------------------------
@Inject
private TextField customerCardId;
@Inject
private TextField tfKontaktperson;
@Inject
private LookupField lfStatus;
@Inject
private LookupField lfProcessGroup;
@Inject
private DateField dfDeadline;
@Inject
private PickerField customerId;
@Inject
private SearchPickerField<Artkl> spArticleNr;
@Inject
private Button btnSaveAndNew;
@Inject
private Button btnSave;
@Inject
private TabSheet tabSheet;
// Beschreibung:
@Named("gbDesc")
private GroupBoxLayout gbDesc;
@Inject
private RichTextArea rtfDesc; // beschreibung
// Data Grid - VorgangsHistorie:
@Named("GbHistory")
private GroupBoxLayout gbHistory;
@Inject
private DataGrid<VorgangHistorie> vorgangshistorieDataGrid;
@Named("vorgangshistorieDataGrid.edit")
private EditAction vorgangshistorieDataGridEditAction;
@Named("vorgangshistorieDataGrid.create")
private CreateAction vorgangshistorieDataGridCreateAction;
@Subscribe
public void onInit(InitEvent initEvent) {
super.addInitEntityListener(event -> {
//default parameter:
event.getEntity().setKontaktrichtung(Kontaktrichtung.fromId("Inbound"));
event.getEntity().setStatus(Status.fromId("Offen"));
event.getEntity().setExportSperre(JaNein.Nein);
event.getEntity().setRueckmeldungErwuenscht(JaNein.Nein);
// no history creation allowed
this.gbHistory.setVisible(false);
this.gbDesc.setVisible(true);
});
// Validator fuer Vorgangs-Status
lfStatus.addValidator(value -> {
Status status = (Status) value;
if(status.equals(Status.inArbeit) && dfDeadline.getValue() == null){
throw new ValidationException(messages.getMessage(this.getClass(),"validation.error.deadlineNotSet"));
}
});
// dynamischer Filter fuer Vorgangskategorien:
lfProcessGroup.addValueChangeListener(e -> {
HasValue.ValueChangeEvent<VorgangGruppe> event = (HasValue.ValueChangeEvent<VorgangGruppe>)e;
if (event.getValue() != null) {
vorgangskategoriesDc.refresh();
List<Vorgangskategorie> allCategories = new ArrayList<>(vorgangskategoriesDc.getItems());
vorgangskategoriesDc.clear(); // ??
allCategories.stream().filter(e2 -> e2.getVorgangGruppe().equals(event.getValue())).forEach(vorgangskategoriesDc::addItem);
}else{
vorgangskategoriesDc.refresh();
}
});
// Automatisches Laden des Kunden anhand der Kartennummer:
customerCardId.addValueChangeListener(event -> {
HasValue.ValueChangeEvent<Long> e = (HasValue.ValueChangeEvent<Long>)event;
// update collection to filter by input:
kndKrtnsDc.refresh();
// get actual item by input - should be available after refresh:
KndKrtn kndKrte = kndKrtnsDc.getItem(e.getValue());
if(kndKrte != null && kndKrte.getKndNr() != null) {
getEditedEntity().setKndNr(kndKrte.getKndNr());
}else{
this.notifications.create().withCaption("Failed to set customer value!").withType(Notifications.NotificationType.TRAY).show();
}
});
// Standard Kontaktperson:
customerId.addValueChangeListener(event -> {
HasValue.ValueChangeEvent<KndDtn> e = (HasValue.ValueChangeEvent<KndDtn>) event;
if(e.getValue() != null && e.getValue() instanceof KndDtn && tfKontaktperson!=null && ( tfKontaktperson.getRawValue() == null || tfKontaktperson.getRawValue().isEmpty() )){
//set default kontaktperson
tfKontaktperson.setValue(messages.getMessage(this.getClass(),"defaultKontaktperson"));
}
if(e.getValue() != null && e.getValue() instanceof KndDtn) {
updateKndVorgengeTabVisibility((KndDtn) e.getValue());
}
});
// Layout fuer Vorgangshistorie:
vorgangshistorieDataGrid.setDetailsGenerator(new DataGrid.DetailsGenerator<VorgangHistorie>() {
@Nullable
@Override
public Component getDetails(VorgangHistorie entity) {
VBoxLayout mainLayout = uiComponents.create(VBoxLayout.class);
mainLayout.setWidth("100%");
mainLayout.setMargin(true);
mainLayout.setSpacing(true);
Label contentLabel = uiComponents.create(Label.class);
contentLabel.setHtmlEnabled(true);
contentLabel.setWidth("98%");
if(entity == null || entity.getText() == null){
contentLabel.setValue("-");
}else{
contentLabel.setValue(entity.getText());
}
mainLayout.add(contentLabel);
mainLayout.expand(contentLabel);
return mainLayout;
}
});
/* close Button für Vorgangshistorie Ansicht:
DataGrid.Column column = vorgangshistorieDataGrid.addGeneratedColumn("closeButton",
new DataGrid.ColumnGenerator<VorgangHistorie, Component>() {
int i = 0;
@Override
public Component getValue(DataGrid.ColumnGeneratorEvent<VorgangHistorie> event){
Button closeButton = componentsFactory.createComponent(Button.class);
closeButton.setIcon("icons/remove.png");
closeButton.setCaption("");
closeButton.setId("closeButton "+i);
closeButton.setAction(new BaseAction("closeDetailsId"){
@Override
public void actionPerform(Component component){
hideVorgangHistorieItemDetails(event.getItem());
}
});
return closeButton;
}
@Override
public Class<Component> getType() {
return Component.class;
}
}
);
column.setRenderer(new WebComponentRenderer());
*/
// Vorgangshistorie: toggle details on click
vorgangshistorieDataGrid.addItemClickListener(event -> {
if(vorgangshistorieDataGrid.isDetailsVisible(event.getItem())) {
vorgangshistorieDataGrid.setDetailsVisible(event.getItem(), false);
}else{
vorgangshistorieDataGrid.setDetailsVisible(event.getItem(), true);
}
});
// Vorgangshistorie: Update Table after insert/update
vorgangshistorieDataGridEditAction.setAfterCommitHandler(entity ->
refreshAndShowDetailsInHistory()
);
vorgangshistorieDataGridCreateAction.setAfterCommitHandler(entity ->
refreshAndShowDetailsInHistory()
);
// on create action: set vorgang id in vorgang historie:
vorgangshistorieDataGridCreateAction.setInitialValuesSupplier(
()-> ParamsMap.of("vorgang", vorgangDc.getItem())
);
if (PersistenceHelper.isNew(getEditedEntity())) {
btnSaveAndNew.setVisible(true);
btnSave.setVisible(false);
}else{
btnSaveAndNew.setVisible(false);
btnSave.setVisible(true);
}
if(getEditedEntity() != null){
this.updateKndVorgengeTabVisibility(getEditedEntity().getKndNr());
}
refreshAndShowDetailsInHistory();
}
/* Vorgangshistorie: for close button!
private void hideVorgangHistorieItemDetails(VorgangHistorie entity){
vorgangshistorieDataGrid.setDetailsVisible(entity, false);
}
*/
private void refreshAndShowDetailsInHistory(){
vorgangHistoriesDc.refresh();
// show details for all items in history:
for (VorgangHistorie item : vorgangHistoriesDc.getItems()) {
vorgangshistorieDataGrid.setDetailsVisible(item, true);
}
}
@Subscribe
private void onBeforeShow(BeforeShowEvent event) {
vorgangDl.load();
}
@Subscribe(id = "vorgangDc", target = Target.DATA_CONTAINER)
private void onCustomerDcItemChange(InstanceContainer.ItemChangeEvent<Vorgang> event) {
vorgangHistoriesDl.setParameter("vorgangId", event.getItem().getId());
vorgangHistoriesDl.load();
kndVorgangsDl.setParameter("vorgangKndNr",event.getItem().getKndNr().getId());
kndVorgangsDl.load();
}
@Subscribe(target = Target.DATA_CONTEXT)
protected void onPreCommit(DataContext.PreCommitEvent event) {
// changed entity
if(vorgangDc.isModified()) {
Vorgang v = this.getEditedEntity();
if(v.getStatus().equals(Status.inArbeit) && v.getTerminAm() == null){
event.preventCommit();
}else if(v.getStatus().equals(Status.offen) && v.getTerminAm() != null){
v.setTerminAm(null);
this.notifications.create(Notifications.NotificationType.TRAY).withCaption(this.messages.getMessage(getClass(),"validation.info.deadlineNull")).show();
}
if(!v.getVorgangskategorie().getVorgangGruppe().equals(v.getVorgangGruppe())){
this.notifications.create(Notifications.NotificationType.TRAY).withCaption(this.messages.getMessage(getClass(),"validation.error.wrongProcessGroup")).show();
event.preventCommit();
}
if(v.getAngelegtAm() == null){
v.setAngelegtAm(new Date());
}
if(v.getAngelegtVon() == null || v.getAngelegtVon().isEmpty()){
v.setAngelegtVon(userSession.getUser().getLoginLowerCase());
}
//set changed date - always!:
v.setGeaendertAm(new Date());
v.setGeaendertVon(userSession.getUser().getLoginLowerCase());
// is not newly created:
if(v.getId()!=null && v.getId().longValue() > 0) {
// Log changes - only if not updated before manually!
// get max Id for history Item:
long maxId = -1;
for(VorgangHistorie veTmp1 : vorgangHistoriesDc.getItems()){
if(veTmp1.getVorgang().getId().longValue() == v.getId().longValue()){
maxId = veTmp1.getId();
}
}
// check last entry:
boolean resultVorgangHistoryEntryExists = false;
Date dTmpXMinBefore = new Date();
dTmpXMinBefore.setTime(System.currentTimeMillis()-(30*60*1000)); // -30 Min
VorgangHistorie veTmp2 = vorgangHistoriesDc.getItem(maxId);
if (
veTmp2.getCreatedBy().equalsIgnoreCase(userSession.getUser().getLoginLowerCase())
&&
!veTmp2.getText().isEmpty()
&&
veTmp2.getCreateTs().before(dTmpXMinBefore)
){
resultVorgangHistoryEntryExists = true;
}
if(!vorgangHistoriesDc.isModified() && !resultVorgangHistoryEntryExists) {
VorgangHistorie vorgangHistorieNewItem = metadata.create(VorgangHistorie.class);
vorgangHistorieNewItem.setVorgang(v);
vorgangHistorieNewItem.setText(this.messages.getMessage(getClass(), "historyCommitLogMessage"));
vorgangHistoriesDc.addItem(vorgangHistorieNewItem);
}
}else{
// Write Description as History Item
VorgangHistorie vorgangHistorieNewItem = metadata.create(VorgangHistorie.class);
vorgangHistorieNewItem.setVorgang(v);
if(rtfDesc.getValue()!=null && !rtfDesc.getValue().isEmpty()) {
vorgangHistorieNewItem.setText(rtfDesc.getValue());
}else{
vorgangHistorieNewItem.setText(this.messages.getMessage(getClass(), "historyCommitLogMessage"));
}
vorgangHistoriesDc.addItem(vorgangHistorieNewItem);
}
}
}
@Subscribe(target = Target.DATA_CONTEXT)
protected void onPostCommit(DataContext.PostCommitEvent postCommitEvent) {
Entity committedEntity = postCommitEvent.getCommittedInstances().stream()
.filter(entity -> entity.equals(getEditedEntity()))
.findFirst()
.get();
Long id = ((Vorgang) committedEntity).getId().longValue();
dialogs.createMessageDialog(Dialogs.MessageType.CONFIRMATION).withCaption("Test").withMessage("ID:" + id).show();
if(vorgangHistoriesDc.isModified()) {
vorgangHistoriesDc.commit();
}
}
private void updateKndVorgengeTabVisibility(KndDtn knd){
TabSheet.Tab t = null;
Iterator <TabSheet.Tab> iterator = tabSheet.getTabs().iterator();
while(iterator.hasNext()){
t = iterator.next();
if(t.getName().contains("kndVorgaengeTab")){
break;
}
}
if(t != null) {
if (knd != null && knd instanceof KndDtn) {
t.setVisible(true);
kndVorgangsDc.refresh();
} else {
t.setVisible(false);
}
}else{
this.notifications.create(Notifications.NotificationType.ERROR).withCaption("Error: Tab not found!").show();
}
}
public void onExportButtonClick() {
List<Report> reports = reportGuiManager.getAvailableReports(getId(),userSession.getUser(),getEditedEntity().getMetaClass());
if(reports.size()>0) {
for (Report r : reports) {
if(r.getName().contains("Vorgangsexport")) {
Map<String,Object> reportParams = new HashMap<>();
reportParams.put("Vorgang",this.getEditedEntity());
reportParams.put("Vorgangshistorie",vorgangHistoriesDc.getItems());
reportGuiManager.printReport(r,reportParams,"DEFAULT","Vorgangsexport");
}
}
}else{
this.notifications.create(Notifications.NotificationType.ERROR).withCaption("Error: No report found!").show();
}
}
public void onBtnCancelClick(){
this.closeWithDiscard();
}
public void onBtnSaveClick() {
this.commitChanges();
}
public void onBtnSaveAndCloseClick() {
this.closeWithCommit();
}
public void onBtnSaveAndNewClick() {
this.commitChanges();
screenBuilders.editor(Vorgang.class, this).withOpenMode(OpenMode.NEW_TAB).editEntity(new Vorgang()).build().show();
}
}
krivopustov
(Konstantin Krivopustov)
May 28, 2019, 6:26am
#14
Please provide the full stack trace. Also, describe how you invoke the screen.
jw90
May 28, 2019, 6:51am
#15
Sorry, I forgot to paste it.
Here is the stacktrace:
java.lang.ClassCastException: de.nexloy.crm.vorgangsverwaltung.web.vorgang.VorgangEdit cannot be cast to com.haulmont.cuba.gui.screen.compatibility.LegacyFrame
at com.haulmont.cuba.gui.sys.UiControllerDependencyInjector.getInjectedInstance(UiControllerDependencyInjector.java:606)
at com.haulmont.cuba.gui.sys.UiControllerDependencyInjector.doInjection(UiControllerDependencyInjector.java:517)
at com.haulmont.cuba.gui.sys.UiControllerDependencyInjector.injectValues(UiControllerDependencyInjector.java:307)
at com.haulmont.cuba.gui.sys.UiControllerDependencyInjector.inject(UiControllerDependencyInjector.java:111)
at com.haulmont.cuba.web.sys.WebScreens.createScreen(WebScreens.java:237)
at com.haulmont.cuba.web.sys.WebScreens.openEditor(WebScreens.java:1175)
at com.haulmont.cuba.gui.config.MenuItemCommands$ScreenCommand.run(MenuItemCommands.java:209)
at com.haulmont.cuba.web.sys.MenuBuilder$MenuCommandExecutor.accept(MenuBuilder.java:256)
at com.haulmont.cuba.web.sys.MenuBuilder$MenuCommandExecutor.accept(MenuBuilder.java:241)
at com.haulmont.cuba.web.gui.components.mainwindow.WebAppMenu$MenuItemImpl.menuSelected(WebAppMenu.java:435)
at com.vaadin.ui.MenuBar.changeVariables(MenuBar.java:225)
at com.vaadin.server.communication.ServerRpcHandler.changeVariables(ServerRpcHandler.java:611)
at com.vaadin.server.communication.ServerRpcHandler.handleInvocation(ServerRpcHandler.java:457)
at com.vaadin.server.communication.ServerRpcHandler.handleInvocations(ServerRpcHandler.java:400)
at com.vaadin.server.communication.ServerRpcHandler.handleRpc(ServerRpcHandler.java:260)
at com.vaadin.server.communication.UidlRequestHandler.synchronizedHandleRequest(UidlRequestHandler.java:82)
at com.vaadin.server.SynchronizedRequestHandler.handleRequest(SynchronizedRequestHandler.java:40)
at com.vaadin.server.VaadinService.handleRequest(VaadinService.java:1577)
at com.vaadin.server.VaadinServlet.service(VaadinServlet.java:425)
at com.haulmont.cuba.web.sys.CubaApplicationServlet.serviceAppRequest(CubaApplicationServlet.java:329)
at com.haulmont.cuba.web.sys.CubaApplicationServlet.service(CubaApplicationServlet.java:215)
at javax.servlet.http.HttpServlet.service(HttpServlet.java:742)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:231)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
at org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
at org.springframework.web.filter.CompositeFilter$VirtualFilterChain.doFilter(CompositeFilter.java:107)
at org.springframework.web.filter.CompositeFilter.doFilter(CompositeFilter.java:73)
at com.haulmont.cuba.web.sys.CubaHttpFilter.doFilter(CubaHttpFilter.java:108)
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:193)
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:166)
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:198)
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:96)
at org.apache.catalina.authenticator.AuthenticatorBase.invoke(AuthenticatorBase.java:493)
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:140)
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:81)
at org.apache.catalina.valves.AbstractAccessLogValve.invoke(AbstractAccessLogValve.java:650)
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:87)
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:342)
at org.apache.coyote.http11.Http11Processor.service(Http11Processor.java:800)
at org.apache.coyote.AbstractProcessorLight.process(AbstractProcessorLight.java:66)
at org.apache.coyote.AbstractProtocol$ConnectionHandler.process(AbstractProtocol.java:806)
at org.apache.tomcat.util.net.NioEndpoint$SocketProcessor.doRun(NioEndpoint.java:1498)
at org.apache.tomcat.util.net.SocketProcessorBase.run(SocketProcessorBase.java:49)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
at org.apache.tomcat.util.threads.TaskThread$WrappingRunnable.run(TaskThread.java:61)
at java.lang.Thread.run(Thread.java:748)
krivopustov
(Konstantin Krivopustov)
May 30, 2019, 4:54am
#16
You have fields with invalid types in the controller:
@Inject
private CollectionDatasource<VorgangHistorie, Long> vorgangHistoriesDc;
@Inject
private Datasource<Vorgang> vorgangDc;
They should by CollectionContainer
and InstanceContainer
respectively. Remove all data source fields and inject them using the Studio Inject dialog to ensure correct types.
jw90
June 4, 2019, 7:06am
#17
Hi again,
thank you for all you help. I really appreciate it.
I rewrote or moved everything accordingly to CUBA 7 and removed all cases of legacy screens.
In the above case everything works now.
I just still have an open issue, which I cannot resolve and hope you’ll help me out again.
In some screens the container is filled with entities, but the content is missing:
What I think is weird, that CUBA itself can load the entities in the entity viewer. Furthermore I haven’t changed the entity implementation in some of these cases, so they should work like before.
I also checked all implementations about a dozen times and in simple screens they are all about the same, but in some of them it works, and in some of them it does not.
It might be related to the overall size of the tables, but I think that’s unlikely, because it worked before.
Do you have any idea, where to look for the problem?
I have ruled out for me:
Entity + View (no changes since CUBA 6.10)
Screen descriptor
different cases with similar implementation, that work
Screen controller
cases without any class implementation, just the base “StandardLookup” or “StandardEditor”
Kind regards,
J
krivopustov
(Konstantin Krivopustov)
June 6, 2019, 7:20am
#18
Hi,
Probably something is wrong with connecting your visual components to data components. Check how you specify properties of the Table, Form, etc. components. Pay attention to IDE warnings.
jw90
June 7, 2019, 12:49pm
#19
Hi again,
thank you again for your reply.
Sadly I do not have any warning or errors in CUBA Studio, which I can check.
I checked also everything again and tried some different settings, but could not even find a single hint, about what might be wrong with it. Maybe I’m just blind from working with CUBA Platform 6. I really do not know it.
Thats why I have to depend on your experience, again.
My browse screen looks like this.
knd-dtn-browse.xml
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<window xmlns="http://schemas.haulmont.com/cuba/screen/window.xsd"
caption="msg://browseCaption"
messagesPack="de.nexloy.crm.vorgangsverwaltung.web.knddtn">
<data>
<collection id="kndDtnsDc" class="de.nexloy.crm.vorgangsverwaltung.entity.KndDtn" view="KndDtn-screen-view">
<loader id="kndDtnsDl">
<query><![CDATA[select e from vorgangsverwaltung$KndDtn e ]]></query>
</loader>
</collection>
</data>
<dialogMode height="AUTO" width="AUTO"/>
<layout expand="kndDtnsTable" spacing="true">
<filter id="filter"
applyTo="kndDtnsTable"
dataLoader="kndDtnsDl"
manualApplyRequired="true"
useMaxResults="true">
<custom caption="msg://kndKrtnNr" join="left join vorgangsverwaltung$KndKrtn e2" name="KndKrtnNr"
paramClass="java.lang.Long"><![CDATA[e2.kndNr = {E} and e2.id = ?]]></custom>
<property caption="msg://kndNr" name="id"/>
<property caption="msg://vorname" name="vorname"/>
<property caption="msg://nachname" name="nachname"/>
<property caption="msg://gbrt_datum" name="gbrtDatum"/>
</filter>
<groupTable id="kndDtnsTable" width="100%" dataContainer="kndDtnsDc">
<actions>
<action id="refresh" type="refresh"/>
<action id="edit" type="edit"/>
</actions>
<columns>
<column id="id" caption="msg://kndNr"/>
<column id="kndTyp" caption="msg://kndTyp" visible="false"/>
<column id="titel" caption="msg://titel" visible="false"/>
<column id="anrede" caption="msg://anrede" visible="false"/>
<column id="nachname" caption="msg://nachname"/>
<column id="vorname" caption="msg://vorname"/>
<column id="gbrtDatum" caption="msg://gbrt_datum"/>
<column id="geschlecht" caption="msg://geschlecht" visible="false"/>
<column id="firma" caption="msg://firma" visible="false"/>
<column id="strasse" caption="msg://strasse" visible="false"/>
<column id="hausNr" caption="msg://hausNr" visible="false"/>
<column id="postleitzahl" caption="msg://plz"/>
<column id="ort" caption="msg://ort"/>
<column id="plzLand" caption="msg://plzLand" visible="false"/>
<column id="telNr" caption="msg://telNr"/>
<column id="eMail" caption="msg://eMail"/>
<column id="mobilTelNr" caption="msg://mobilTelNr"/>
</columns>
<rowsCount/>
<buttonsPanel id="buttonsPanel" alwaysVisible="true">
<button id="open" action="kndDtnsTable.edit" caption="msg://open"/>
<button id="refreshBtn" action="kndDtnsTable.refresh" caption="msg://refresh"/>
</buttonsPanel>
</groupTable>
<hbox id="lookupActions" spacing="true" visible="false">
<button action="lookupSelectAction"/>
<button action="lookupCancelAction"/>
</hbox>
</layout>
</window>
KndDtnBrowse.java
package de.nexloy.crm.vorgangsverwaltung.web.knddtn;
import com.haulmont.cuba.gui.screen.*;
import de.nexloy.crm.vorgangsverwaltung.entity.KndDtn;
@UiController("vorgangsverwaltung$KndDtn.browse")
@UiDescriptor("knd-dtn-browse.xml")
@LookupComponent("kndDtnsTable")
@PrimaryLookupScreen(KndDtn.class)
@LoadDataBeforeShow
public class KndDtnBrowse extends StandardLookup<KndDtn> {
}
krivopustov
(Konstantin Krivopustov)
June 10, 2019, 11:46am
#20
Please try to extract the problematic entities and screens to a test project were we could reproduce the issue.
jw90
June 12, 2019, 11:41am
#21
Hi,
I think I found the reason for my problem.
I recreated some screens from scratch and it worked on the new screens. Then I merged the changes until it did not work anymore.
The reason it did not work is, that the “data” tag was not marked as readonly=“true”.
The database table is read only, but the entity in CUBA is not defined as read only. It seems, that in CUBA 7, it still needs to be declared as read only, but only when the entity base class is “BaseLongIdEntity”.
Before and not working:
<!-- ... -->
<data>
<collection id="kndDtnsDc" class="de.nexloy.crm.vorgangsverwaltung.entity.KndDtn" view="KndDtn-screen-view">
<loader id="kndDtnsDl">
<query><![CDATA[select e from vorgangsverwaltung$KndDtn e ]]></query>
</loader>
</collection>
</data>
<!-- ... -->
Afterwards and working:
<!-- ... -->
<data readOnly="true">
<collection id="kndDtnsDc"
class="de.nexloy.crm.vorgangsverwaltung.entity.KndDtn"
view="KndDtn-screen-view">
<loader id="kndDtnsDl">
<query>
<![CDATA[select e from vorgangsverwaltung$KndDtn e]]>
</query>
</loader>
</collection>
</data>
<!-- ... -->
I hope you can explain me, why that makes a difference. I still do not quite understand, why this is important.
Kind regards,
J
krivopustov
(Konstantin Krivopustov)
June 14, 2019, 11:09am
#22
Hi,
This is not normal, browser screens without readOnly="true"
work well with entities extending BaseLongIdEntity
.
Please provide a test project.
krivopustov
(Konstantin Krivopustov)
June 18, 2019, 8:18am
#24
Sure, please provide DDL for the Oracle table corresponding to KndDtn
entity.
krivopustov
(Konstantin Krivopustov)
June 20, 2019, 10:29am
#26
Hi,
As it turned out after investigation, the cause is that your entity does not have setters for the most fields, so the attributes are effectively read-only. It prevents the state to be merged into DataContext (until it is not read-only).
So just add all standard getters and setters, and your entity will be displayed correctly in all screens.
Regards,
Konstantin