Hi everyone. in several views i have problems with invisible components which are not showing up after first start of the app. Only after reload of the page (F5 or cmd+r) the components become visible.
In the code bewlow it is the mail-Field. It is invisible once i start the app and visit the view. When i reload the page it becomes visible. But the other name und firstname are visible!
The same issue i have in other views where i use Font Awesome Icon on buttons. They become only visible when i reload the page. Does anyone knows what this could be?
The problem only occur only after mvn clean package -Pproduction. When i run it in my IDE it works.
I have updated already to 24.6.6, did the vaadin dance but it wont work. I am using Java 21
In the browser console i see following errors (in this view is no split layout used, dont know why it thows an error).
This problem comes up when i switched from 24.5.0 to a higher version. My productive branch is still in 24.5.0 and there i cant reproduce this error.
Here is the mentioned View where it occurs:
Code
`@Route(value = “user”, layout = MainView.class)
@PageTitle(“Benutzerverwaltung”)
@RolesAllowed({SecurityRoles.ROLE_REHNTIER_VIEW, SecurityRoles.ROLE_USERMANAGEMENT_VIEW})
public class UserManagementView extends FormLayout {
PasswordEncoder passwordEncoder = (PasswordEncoder) ApplicationContextProvider.getApplicationContext().getBean("encoder");
PasswordField p1 = new PasswordField("Password");
PasswordField p2 = new PasswordField("Password repeat");
UserDetailsServiceImpl userService = SpringContext.getBean(UserDetailsServiceImpl.class);
UserRoleService userRoleService = SpringContext.getBean(UserRoleService.class);
Binder<User> binderUserDetails = new Binder<>(User.class);
List<User> userList = new ArrayList<>();
User user = new User();
TextField username = new TextField(getTranslation("username"));
TextField firstName = new TextField(getTranslation("firstname"));
TextField lastName = new TextField(getTranslation("lastname"));
Checkbox enabled = new Checkbox(getTranslation("active"));
EmailField mail = new EmailField(getTranslation("email"));
Grid<String> permissionGrid = new Grid();
Button createNewUserButton = new Button(getTranslation("add") + " " + getTranslation("user"), VaadinIcon.PLUS.create());
private ColoredVerticalLayout userDataPanel;
private ColoredVerticalLayout permissionPanel;
private Map<String, Checkbox> roleCheckboxes = new HashMap<>();
public UserManagementView() {
initUserDetailList();
bindAllFields();
createNewUserButton.addClickListener(event -> showNewUserDialog());
HorizontalLayout horizontalLayout = new HorizontalLayout();
horizontalLayout.setPadding(true);
horizontalLayout.setAlignItems(FlexComponent.Alignment.BASELINE);
horizontalLayout.setVerticalComponentAlignment(FlexComponent.Alignment.BASELINE);
horizontalLayout.add(createSelectUser(), createNewUserButton);
this.add(horizontalLayout, 2);
VerticalLayout verticalLayoutUserData = new VerticalLayout();
verticalLayoutUserData.setPadding(false);
verticalLayoutUserData.setWidth("100%");
userDataPanel = new ColoredVerticalLayout(createUserDataPanel(), getTranslation("user"), VaadinIcon.USER_CARD);
userDataPanel.setEnabled(false);
verticalLayoutUserData.add(userDataPanel);
this.add(verticalLayoutUserData);
refreshCheckboxesBasedOnUserRoles();
VerticalLayout verticalLayoutPermissions = new VerticalLayout();
verticalLayoutPermissions.setPadding(false);
verticalLayoutPermissions.setWidth("100%");
permissionPanel = new ColoredVerticalLayout(createPermissionsPanel(), getTranslation("usermanagementview.permissions"), VaadinIcon.SIGN_IN);
permissionPanel.setEnabled(false);
verticalLayoutPermissions.add(permissionPanel);
this.add(verticalLayoutPermissions);
mail.setErrorMessage(getTranslation("error.validation.failed"));
}
private void refreshCheckboxesBasedOnUserRoles() {
if (user.getUserRoles() != null) {
for (UserRole userRole : user.getUserRoles()) {
Checkbox correspondingCheckbox = roleCheckboxes.get(userRole.getUserRoleName());
if (correspondingCheckbox != null) {
correspondingCheckbox.setValue(true);
}
}
}
}
private Component createUserDataPanel() {
FormLayoutFlexColumns formLayout = new FormLayoutFlexColumns(3);
formLayout.add(firstName);
formLayout.add(lastName);
formLayout.add(mail);
formLayout.add(enabled, 3);
formLayout.add(createSaveUserButton());
formLayout.add(createDeleteButton());
formLayout.add(createResetPasswordButton());
return formLayout;
}
private Component createPermissionsPanel() {
VerticalLayout verticalLayout = new VerticalLayout();
permissionGrid.addColumn(item -> getTranslation(item)).setHeader("Permission");
permissionGrid.addComponentColumn(item -> isRoleAllowed(item)).setHeader("Access Permited");
verticalLayout.add(permissionGrid);
return verticalLayout;
}
private Component createResetPasswordButton() {
FormLayout formLayout = new FormLayout();
formLayout.getStyle().set("padding", "15px");
formLayout.add(p1);
formLayout.add(p2);
formLayout.add(createUpdatePasswordButton());
Button button = new Button("Reset Password");
button.addClickListener(buttonClickEvent -> {
DialogWithTitleBar dialog = new DialogWithTitleBar("Reset Password", formLayout, 50);
dialog.open();
});
return button;
}
private void showNewUserDialog() {
VerticalLayout verticalLayout = new VerticalLayout();
TextField userNameTf = new TextField(getTranslation("username"));
TextField userFirstNameTf = new TextField(getTranslation("firstname"));
TextField userLastTf = new TextField(getTranslation("lastname"));
TextField userEmailTf = new TextField(getTranslation("email"));
PasswordField passwordField1 = new PasswordField(getTranslation("password"));
PasswordField passwordField2 = new PasswordField(getTranslation("passwordRepeat"));
verticalLayout.add(userNameTf);
verticalLayout.add(userFirstNameTf);
verticalLayout.add(userLastTf);
verticalLayout.add(userEmailTf);
verticalLayout.add(passwordField1);
verticalLayout.add(passwordField2);
Button saveButton = new Button(getTranslation("save"), VaadinIcon.LOCK.create());
verticalLayout.add(saveButton);
DialogWithTitleBar dialogWithTitleBar = new DialogWithTitleBar(verticalLayout, "70%", "70%");
saveButton.addClickListener(event -> {
if (userNameTf.getValue() != null && !userNameTf.getValue().equalsIgnoreCase("") && passwordField1.getValue().equals(passwordField2.getValue())) {
User user = new User();
user.setUsername(userNameTf.getValue());
user.setPassword(passwordEncoder.encode(passwordField1.getValue()));
user.setEnabled(true);
user.setFirstName(userFirstNameTf.getValue());
user.setFirstName(userFirstNameTf.getValue());
user.setLastName(userLastTf.getValue());
user.setMail(userEmailTf.getValue());
user.setAccountNonLocked(true);
user.setCredentialsNonExpired(true);
userService.save(user);
dialogWithTitleBar.close();
UI.getCurrent().getPage().reload();
NotificationUtil.getSavedSuccesful().open();
} else {
NotificationUtil.getDynamicNotification(Emoji.WARN, getTranslation("usermanagementview.userwrong")).open();
}
});
verticalLayout.add(new Span(getTranslation("usermanagementview.infoaftersave")));
dialogWithTitleBar.open();
}
private void selectUserChangeListener(AbstractField.ComponentValueChangeEvent<Select<User>, User> e) {
if (e.getValue() != null && !e.getValue().getUsername().equals("")) {
user = userService.findByUsername(e.getValue().getUsername());
binderUserDetails.readBean(user);
userDataPanel.setEnabled(true);
permissionPanel.setEnabled(true);
updatePermissionGrid();
}
}
private void updatePermissionGrid() {
Map<String, String> map = SecurityRoles.getRoles();
List<String> allRoles = new ArrayList();
for (Map.Entry<String, String> entry : map.entrySet()) {
allRoles.add(entry.getValue());
}
permissionGrid.setItems(allRoles);
}
private Component createSelectUser() {
Select<User> selectUser = new Select<>();
selectUser.setWidth("300px");
selectUser.setLabel("Login Name");
selectUser.setPlaceholder(getTranslation("choose"));
selectUser.setItems(userList);
selectUser.setItemLabelGenerator(User::getUsername);
selectUser.addValueChangeListener((e) -> selectUserChangeListener(e));
return selectUser;
}
private Component createDeleteButton() {
Button deleteButton = new Button(getTranslation("delete"), VaadinIcon.TRASH.create());
deleteButton.addClickListener(event -> {
ConfirmDialog dialog = new ConfirmDialog();
dialog.setHeader(getTranslation("record") + " " + getTranslation("delete"));
dialog.setText(getTranslation("dialog.delete"));
dialog.setCancelable(true);
dialog.addCancelListener(cancelEvent -> {
dialog.close();
});
dialog.setRejectable(false);
dialog.setCancelText(getTranslation("cancel"));
dialog.setConfirmText(getTranslation("delte"));
dialog.addConfirmListener(confirmEvent -> {
deleteUserData(user, dialog);
});
dialog.open();
});
return deleteButton;
}
private void deleteUserData(User user, ConfirmDialog dialog) {
userService.delete(user);
userRoleService.removeAllRoles(user.getId());
dialog.close();
UI.getCurrent().getPage().reload();
NotificationUtil.getDynamicNotification(Emoji.THUMB_UP, getTranslation("notification.proceeded.sucessfully")).open();
}
private void initUserDetailList() {
userList = userService.findAllWithoutRehntier();
}
private Component createUpdatePasswordButton() {
Button button = new Button(getTranslation("updatepassword"), new Icon(VaadinIcon.LOCK));
button.addClickListener(event -> {
String value1 = p1.getValue();
String value2 = p2.getValue();
if (value1.equals(value2)) {
userService.updatePassword(user.getId(), username.getValue(), passwordEncoder.encode(value1));
NotificationUtil.getSavedSuccesful().open();
NotificationUtil.getDynamicNotification(Emoji.WARN, getTranslation("notification.loginlogout")).open();
} else {
NotificationUtil.getDynamicNotification(Emoji.SCREAM_FACE, getTranslation("notification.passwordnotmatching")).open();
}
});
return button;
}
private Component createSaveUserButton() {
Button button = new Button(getTranslation("save"), new Icon(VaadinIcon.LOCK));
button.addClickListener((e) -> saveUser());
return button;
}
private void saveUser() {
try {
// user.setPassword(passwordEncoder.encode(password.getValue()));
binderUserDetails.writeBean(user);
userService.save(user);
NotificationUtil.getSavedSuccesful().open();
} catch (ValidationException e) {
e.printStackTrace();
}
}
void checkboxValueChanged(AbstractField.ComponentValueChangeEvent<Checkbox, Boolean> e, String roleName) {
String roleEnum = SecurityRoles.getRoleEnumByRoleName(roleName);
if (e.getValue()) {
if (!isRoleAlreadyAllowed(roleEnum)) {
userRoleService.addRole(user.getId(), roleEnum);
NotificationUtil.getSavedSuccesful().open();
NotificationUtil.getDynamicNotification(Emoji.WARN, getTranslation("notification.loginlogout")).open();
}
} else {
userRoleService.removeRole(user.getId(), roleEnum);
NotificationUtil.getSavedSuccesful().open();
NotificationUtil.getDynamicNotification(Emoji.WARN, getTranslation("notification.loginlogout")).open();
}
}
private Component isRoleAllowed(String role) {
String roleEnum = SecurityRoles.getRoleEnumByRoleName(role);
boolean allowed = false;
if (user.getUserRoles() != null) {
for (UserRole userRole : user.getUserRoles()) {
if (userRole.getUserRoleName().toString().equals(roleEnum)) {
allowed = true;
break;
}
}
}
Checkbox cb = new Checkbox();
cb.setValue(allowed);
cb.addValueChangeListener((e) -> checkboxValueChanged(e, role));
return cb;
}
private boolean isRoleAlreadyAllowed(String role) {
boolean allowed = false;
if (user.getUserRoles() != null) {
for (UserRole userRole : user.getUserRoles()) {
if (userRole.getUserRoleName().equals(role)) {
allowed = true;
break;
}
}
}
return allowed;
}
private void bindAllFields() {
binderUserDetails.bind(firstName, "firstName");
binderUserDetails.bind(lastName, "lastName");
binderUserDetails.bind(username, "username");
binderUserDetails.bind(mail, "mail");
binderUserDetails.bind(enabled, "enabled");
binderUserDetails.readBean(user);
}
}`
When i switch back to 24.4.22 everything works like expected! Looks like a bug
Edit: sometimes it works, sometimes not. I dont get it